🔍 搜尋結果:JavaScript

🔍 搜尋結果:JavaScript

建立文字到 PowerPoint 應用程式(LangChain、Next.js 和 CopilotKit)

長話短說 ==== 在本文中,您將學習如何建立由 AI 驅動的 PowerPoint 應用程式,該應用程式可以搜尋網路以自動製作有關任何主題的簡報。 我們將介紹使用: - 用於應用程式框架的 Next.js 🖥️ - 法學碩士 OpenAI 🧠 - LangChain 和 Tavily 的網路搜尋人工智慧代理🤖 - 使用 CopilotKit 將 AI 整合到您的應用程式中 🪁 ![圖片描述](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ztokmi3hdcthmxkj2gny.gif) --- CopilotKit:為您的應用程式建立人工智慧副駕駛 --------------------------- CopilotKit 是[開源人工智慧副駕駛平台。](https://github.com/CopilotKit/CopilotKit)我們可以輕鬆地將強大的人工智慧整合到您的 React 應用程式中。 建造: - ChatBot:上下文感知的應用內聊天機器人,可以在應用程式內執行操作 💬 - CopilotTextArea:人工智慧驅動的文字字段,具有上下文感知自動完成和插入功能📝 - 聯合代理:應用程式內人工智慧代理,可以與您的應用程式和使用者互動🤖 ![圖片描述](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/h69i50cxsyvcknlcs6q0.gif) {% cta https://github.com/CopilotKit/CopilotKit %} Star CopilotKit ⭐️ {% endcta %} 現在回到文章。 (本文是我們三週前發表的一篇文章的進展,但您無需閱讀該文章即可理解這一點)。 --- **先決條件** -------- 在開始建立應用程式之前,讓我們先查看建置應用程式所需的依賴項或套件 `copilotkit/react-core` :CopilotKit 前端包,帶有 React hooks,用於向副駕駛提供應用程式狀態和操作(AI 功能) `copilotkit/react-ui` :聊天機器人側邊欄 UI 的 CopilotKit 前端包 `copilotkit/react-textarea` :CopilotKit 前端包,用於在演講者筆記中進行人工智慧輔助文字編輯。 `LangChainJS` :一個用於開發由語言模型支援的應用程式的框架。 `Tavily Search API` :幫助將法學碩士和人工智慧應用程式連接到可信賴的即時知識的 API。 安裝所有專案包和依賴項 ----------- 在安裝所有專案包和依賴項之前,我們首先在終端機上執行以下命令來建立 Nextjs 專案。 ``` npx create-next-app@latest ``` 然後系統會提示您選擇一些選項。請隨意標記它們,如下所示。 ![建立 Nextjs 專案](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/n668ixcvu5lnrsm9jpmq.png) 之後,使用您選擇的文字編輯器開啟新建立的 Nextjs 專案。然後在命令列中執行以下命令來安裝所有專案包和依賴項。 ``` npm i @copilotkit/backend @copilotkit/shared @langchain/langgraph @copilotkit/react-core @copilotkit/react-ui @copilotkit/react-textarea @heroicons/react ``` **建立 PowerPoint 應用程式前端** ------------------------ 讓我們先建立一個名為`Slide.tsx`的檔案。該文件將包含顯示和編輯投影片內容的程式碼,包括其`title` 、 `body text` 、 `background image`和`spoken narration text` 。 要建立該文件,請前往`/[root]/src/app`並建立一個名為`components`的資料夾。在 Components 資料夾中,建立`Slide.tsx`檔案。 之後,在文件頂部加入以下程式碼。程式碼定義了兩個名為`SlideModel`和`SlideProps`的 TypeScript 介面。 ``` "use client"; // Define an interface for the model of a slide, specifying the expected structure of a slide object. export interface SlideModel { title: string; content: string; backgroundImageDescription: string; spokenNarration: string; } // Define an interface for the properties of a component or function that manages slides. export interface SlideProps { slide: SlideModel; partialUpdateSlide: (partialSlide: Partial<SlideModel>) => void; } ``` 接下來,在上面的程式碼下面加入以下程式碼。程式碼定義了一個名為`Slide`功能元件,它接受`SlideProps`類型的 props。 ``` // Define a functional component named Slide that accepts props of type SlideProps. export const Slide = (props: SlideProps) => { // Define a constant for the height of the area reserved for speaker notes. const heightOfSpeakerNotes = 150; // Construct a URL for the background image using the description from slide properties, dynamically fetching an image from Unsplash. const backgroundImage = 'url("https://source.unsplash.com/featured/?' + encodeURIComponent(props.slide.backgroundImageDescription) + '")'; // Return JSX for the slide component. return ( <> {/* Slide content container with dynamic height calculation to account for speaker notes area. */} <div className="w-full relative bg-slate-200" style={{ height: `calc(100vh - ${heightOfSpeakerNotes}px)`, // Calculate height to leave space for speaker notes. }} > {/* Container for the slide title with centered alignment and styling. */} <div className="h-1/5 flex items-center justify-center text-5xl text-white text-center z-10" > {/* Textarea for slide title input, allowing dynamic updates. */} <textarea className="text-2xl bg-transparent text-black p-4 text-center font-bold uppercase italic line-clamp-2 resize-none flex items-center" style={{ border: "none", outline: "none", }} value={props.slide.title} placeholder="Title" onChange={(e) => { props.partialUpdateSlide({ title: e.target.value }); }} /> </div> {/* Container for the slide content with background image. */} <div className="h-4/5 flex" style={{ backgroundImage, backgroundSize: "cover", backgroundPosition: "center", }} > {/* Textarea for slide content input, allowing dynamic updates and styled for readability. */} <textarea className="w-full text-3xl text-black font-medium p-10 resize-none bg-red mx-40 my-8 rounded-xl text-center" style={{ lineHeight: "1.5", }} value={props.slide.content} placeholder="Body" onChange={(e) => { props.partialUpdateSlide({ content: e.target.value }); }} /> </div> </div> {/* Textarea for entering spoken narration with specified height and styling for consistency. */} <textarea className=" w-9/12 h-full bg-transparent text-5xl p-10 resize-none bg-gray-500 pr-36" style={{ height: `${heightOfSpeakerNotes}px`, background: "none", border: "none", outline: "none", fontFamily: "inherit", fontSize: "inherit", lineHeight: "inherit", }} value={props.slide.spokenNarration} onChange={(e) => { props.partialUpdateSlide({ spokenNarration: e.target.value }); }} /> </> ); }; ``` 之後,我們現在會建立一個名為`Presentation.tsx`的檔案。 該文件將包含初始化和更新投影片狀態、渲染目前投影片以及根據目前狀態動態啟用或停用按鈕實現導覽和投影片管理操作的程式碼。 要建立該文件,請將另一個文件新增至元件資料夾中,並將其命名為`Presentation.tsx` ,然後使用下列程式碼在檔案頂部匯入`React hooks` 、 `icons` 、 `SlideModel`和`Slide`元件。 ``` "use client"; import { useCallback, useMemo, useState } from "react"; import { BackwardIcon, ForwardIcon, PlusIcon, SparklesIcon, TrashIcon } from "@heroicons/react/24/outline"; import { SlideModel, Slide } from "./Slide"; ``` 之後,在上面的程式碼下面加入以下程式碼。程式碼定義了一個`ActionButton`功能元件,它將呈現具有可自訂屬性的按鈕元素。 ``` export const ActionButton = ({ disabled, onClick, className, children, }: { disabled: boolean; onClick: () => void; className?: string; children: React.ReactNode; }) => { return ( <button disabled={disabled} className={`bg-blue-500 text-white font-bold py-2 px-4 rounded ${disabled ? "opacity-50 cursor-not-allowed" : "hover:bg-blue-700"} ${className}`} onClick={onClick} > {children} </button> ); }; ``` 然後在上面的程式碼下面加入下面的程式碼。程式碼定義了一個名為「Presentation」的功能元件,用於初始化投影片的狀態並定義一個用於更新目前投影片的函數。 ``` // Define the Presentation component as a functional component. export const Presentation = () => { // Initialize state for slides with a default first slide and a state to track the current slide index. const [slides, setSlides] = useState<SlideModel[]>([ { title: `Welcome to our presentation!`, // Title of the first slide. content: 'This is the first slide.', // Content of the first slide. backgroundImageDescription: "hello", // Description for background image retrieval. spokenNarration: "This is the first slide. Welcome to our presentation!", // Spoken narration text for the first slide. }, ]); const [currentSlideIndex, setCurrentSlideIndex] = useState(0); // Current slide index, starting at 0. // Use useMemo to memoize the current slide object to avoid unnecessary recalculations. const currentSlide = useMemo(() => slides[currentSlideIndex], [slides, currentSlideIndex]); // Define a function to update the current slide. This function uses useCallback to memoize itself to prevent unnecessary re-creations. const updateCurrentSlide = useCallback( (partialSlide: Partial<SlideModel>) => { // Update the slides state by creating a new array with the updated current slide. setSlides((slides) => [ ...slides.slice(0, currentSlideIndex), // Copy all slides before the current one. { ...slides[currentSlideIndex], ...partialSlide }, // Merge the current slide with the updates. ...slides.slice(currentSlideIndex + 1), // Copy all slides after the current one. ]); }, [currentSlideIndex, setSlides] // Dependencies for useCallback. ); // The JSX structure for the Presentation component. return ( <div className="relative"> {/* Render the current slide by passing the currentSlide and updateCurrentSlide function as props. */} <Slide slide={currentSlide} partialUpdateSlide={updateCurrentSlide} /> {/* Container for action buttons located at the top-left corner of the screen. */} <div className="absolute top-0 left-0 mt-6 ml-4 z-30"> {/* Action button to add a new slide. Disabled state is hardcoded to true for demonstration. */} <ActionButton disabled={true} onClick={() => { // Define a new slide object. const newSlide: SlideModel = { title: "Title", content: "Body", backgroundImageDescription: "random", spokenNarration: "The speaker's notes for this slide.", }; // Update the slides array to include the new slide. setSlides((slides) => [ ...slides.slice(0, currentSlideIndex + 1), newSlide, ...slides.slice(currentSlideIndex + 1), ]); // Move to the new slide by updating the currentSlideIndex. setCurrentSlideIndex((i) => i + 1); }} className="rounded-r-none" > <PlusIcon className="h-6 w-6" /> {/* Icon for the button. */} </ActionButton> {/* Another action button, currently disabled and without functionality. */} <ActionButton disabled={true} onClick={async () => { }} // Placeholder async function. className="rounded-l-none ml-[1px]" > <SparklesIcon className="h-6 w-6" /> {/* Icon for the button. */} </ActionButton> </div> {/* Container for action buttons at the top-right corner for deleting slides, etc. */} <div className="absolute top-0 right-0 mt-6 mr-24"> <ActionButton disabled={slides.length === 1} // Disable button if there's only one slide. onClick={() => {}} // Placeholder function for the button action. className="ml-5 rounded-r-none" > <TrashIcon className="h-6 w-6" /> {/* Icon for the button. */} </ActionButton> </div> {/* Display current slide number and total slides at the bottom-right corner. */} <div className="absolute bottom-0 right-0 mb-20 mx-24 text-xl" style={{ textShadow: "1px 1px 0 #ddd, -1px -1px 0 #ddd, 1px -1px 0 #ddd, -1px 1px 0 #ddd", }} > Slide {currentSlideIndex + 1} of {slides.length} {/* Current slide and total slides. */} </div> {/* Container for navigation buttons (previous and next) at the bottom-right corner. */} <div className="absolute bottom-0 right-0 mb-6 mx-24"> {/* Button to navigate to the previous slide. */} <ActionButton className="rounded-r-none" disabled={ currentSlideIndex === 0 || true} // Example condition to disable button; 'true' is just for demonstration. onClick={() => { setCurrentSlideIndex((i) => i - 1); // Update currentSlideIndex to move to the previous slide. }} > <BackwardIcon className="h-6 w-6" /> {/* Icon for the button. */} </ActionButton> {/* Button to navigate to the next slide. */} <ActionButton className="mr-[1px] rounded-l-none" disabled={ true || currentSlideIndex + 1 === slides.length} // Example condition to disable button; 'true' is just for demonstration. onClick={async () => { setCurrentSlideIndex((i) => i + 1); // Update currentSlideIndex to move to the next slide. }} > <ForwardIcon className="h-6 w-6" /> {/* Icon for the button. */} </ActionButton> </div> </div> ); }; ``` 要在瀏覽器上呈現 PowerPoint 應用程式,請前往`/[root]/src/app/page.tsx`檔案並新增以下程式碼。 ``` "use client"; import "./style.css"; import { Presentation } from "./components/Presentation"; export default function AIPresentation() { return ( <Presentation /> ); } ``` 如果您想要在 Powerpoint 應用程式前端新增樣式,請在`/[root]/src/app`資料夾中建立名為`style.css`的檔案。 然後導航[到此 gist 文件](https://gist.github.com/TheGreatBonnie/e7c0b790a2e2af3e669810539ba54fed),複製 CSS 程式碼,並將其新增至 style.css 檔案。 最後,在命令列上執行命令`npm run dev` ,然後導航到 http://localhost:3000/。 現在您應該在瀏覽器上查看 PowerPoint 應用程式,如下所示。 ![PowerPoint應用程式](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/kqcjqqmo1b2oow6y4p76.png) **將 PowerPoint 應用程式與 CopilotKit 後端集成** -------------------------------------- 讓我們先在根目錄中建立一個名為`.env.local`的檔案。然後在保存 ChatGPT 和 Tavily Search API 金鑰的檔案中加入下面的環境變數。 ``` OPENAI_API_KEY="Your ChatGPT API key" TAVILY_API_KEY="Your Tavily Search API key" ``` 若要取得 ChatGPT API 金鑰,請導覽至 https://platform.openai.com/api-keys。 ![ChatGPT API 金鑰](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1u65aswytyym0zpoh5wx.png) 若要取得 Tavilly Search API 金鑰,請導覽至 https://app.tavily.com/home ![泰維利搜尋 API 金鑰](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/6ugx1oqifnk24l69jjkf.png) 之後,轉到`/[root]/src/app`並建立一個名為`api`的資料夾。在`api`資料夾中,建立一個名為`copilotkit`的資料夾。 在`copilotkit`資料夾中,建立一個名為`research.ts`的檔案。然後導航到[該 Research.ts gist 文件](https://gist.github.com/TheGreatBonnie/58dc21ebbeeb8cbb08df665db762738c),複製程式碼,並將其新增至**`research.ts`**檔案中 接下來,在`/[root]/src/app/api/copilotkit`資料夾中建立一個名為`route.ts`的檔案。該文件將包含設定後端功能來處理 POST 請求的程式碼。它有條件地包括對給定主題進行研究的“研究”操作。 現在在文件頂部導入以下模組。 ``` import { CopilotBackend, OpenAIAdapter } from "@copilotkit/backend"; // For backend functionality with CopilotKit. import { researchWithLangGraph } from "./research"; // Import a custom function for conducting research. import { AnnotatedFunction } from "@copilotkit/shared"; // For annotating functions with metadata. ``` 在上面的程式碼下面,定義一個執行時環境變數和一個註解的函數,以便使用下面的程式碼進行研究。 ``` // Define a runtime environment variable, indicating the environment where the code is expected to run. export const runtime = "edge"; // Define an annotated function for research. This object includes metadata and an implementation for the function. const researchAction: AnnotatedFunction<any> = { name: "research", // Function name. description: "Call this function to conduct research on a certain topic. Respect other notes about when to call this function", // Function description. argumentAnnotations: [ // Annotations for arguments that the function accepts. { name: "topic", // Argument name. type: "string", // Argument type. description: "The topic to research. 5 characters or longer.", // Argument description. required: true, // Indicates that the argument is required. }, ], implementation: async (topic) => { // The actual function implementation. console.log("Researching topic: ", topic); // Log the research topic. return await researchWithLangGraph(topic); // Call the research function and return its result. }, }; ``` 然後在上面的程式碼下加入下面的程式碼來定義處理POST請求的非同步函數。 ``` // Define an asynchronous function that handles POST requests. export async function POST(req: Request): Promise<Response> { const actions: AnnotatedFunction<any>[] = []; // Initialize an array to hold actions. // Check if a specific environment variable is set, indicating access to certain functionality. if (process.env["TAVILY_API_KEY"]) { actions.push(researchAction); // Add the research action to the actions array if the condition is true. } // Instantiate CopilotBackend with the actions defined above. const copilotKit = new CopilotBackend({ actions: actions, }); // Use the CopilotBackend instance to generate a response for the incoming request using an OpenAIAdapter. return copilotKit.response(req, new OpenAIAdapter()); } ``` **將 PowerPoint 應用程式與 CopilotKit 前端集成** -------------------------------------- 讓我們先導入`/[root]/src/app/components/Slide.tsx`檔案頂部的`useMakeCopilotActionable`掛鉤。 ``` import { useMakeCopilotActionable } from "@copilotkit/react-core"; ``` 在 Slide 函數中,新增以下程式碼,該程式碼使用`useMakeCopilotActionable`掛鉤來設定一個名為`updateSlide`的操作,該操作具有特定參數以及根據提供的值更新投影片的實作。 ``` useMakeCopilotActionable({ // Defines the action name. This is a unique identifier for the action within the application. name: "updateSlide", // Describes what the action does. In this case, it updates the current slide. description: "Update the current slide.", // Details the arguments that the action accepts. Each argument has a name, type, description, and a flag indicating if it's required. argumentAnnotations: [ { name: "title", // The argument name. type: "string", // The data type of the argument. description: "The title of the slide. Should be a few words long.", // Description of the argument. required: true, // Indicates that this argument must be provided for the action to execute. }, { name: "content", type: "string", description: "The content of the slide. Should generally consists of a few bullet points.", required: true, }, { name: "backgroundImageDescription", type: "string", description: "What to display in the background of the slide. For example, 'dog', 'house', etc.", required: true, }, { name: "spokenNarration", type: "string", description: "The spoken narration for the slide. This is what the user will hear when the slide is shown.", required: true, }, ], // The implementation of the action. This is a function that will be called when the action is executed. implementation: async (title, content, backgroundImageDescription, spokenNarration) => { // Calls a function passed in through props to partially update the slide with new values for the specified properties. props.partialUpdateSlide({ title, content, backgroundImageDescription, spokenNarration, }); }, }, [props.partialUpdateSlide]); // Dependencies array for the custom hook or function. This ensures that the action is re-initialized only when `props.partialUpdateSlide` changes. ``` 之後,請前往`/[root]/src/app/components/Presentation.tsx`檔案並使用下面的程式碼匯入頂部的 CopilotKit 前端套件。 ``` import { useCopilotContext } from "@copilotkit/react-core"; import { CopilotTask } from "@copilotkit/react-core"; import { useMakeCopilotActionable, useMakeCopilotReadable } from "@copilotkit/react-core"; ``` 在演示函數中,加入以下程式碼,該程式碼使用`useMakeCopilotReadable`掛鉤加入`Slides`和`currentSlide`幻燈片陣列作為應用程式內聊天機器人的上下文。掛鉤使副駕駛可以讀取簡報中的整個幻燈片集合以及當前幻燈片的資料。 ``` useMakeCopilotReadable("These are all the slides: " + JSON.stringify(slides)); useMakeCopilotReadable( "This is the current slide: " + JSON.stringify(currentSlide) ); ``` 在`useMakeCopilotReadable`掛鉤下方,新增以下程式碼,該程式碼使用`useCopilotActionable`掛鉤來設定名為`appendSlide`的操作,其中包含說明和加入多張幻燈片的實作函數。 ``` useMakeCopilotActionable( { // Defines the action's metadata. name: "appendSlide", // Action identifier. description: "Add a slide after all the existing slides. Call this function multiple times to add multiple slides.", // Specifies the arguments that the action takes, including their types, descriptions, and if they are required. argumentAnnotations: [ { name: "title", // The title of the new slide. type: "string", description: "The title of the slide. Should be a few words long.", required: true, }, { name: "content", // The main content or body of the new slide. type: "string", description: "The content of the slide. Should generally consist of a few bullet points.", required: true, }, { name: "backgroundImageDescription", // Description for fetching or generating the background image of the new slide. type: "string", description: "What to display in the background of the slide. For example, 'dog', 'house', etc.", required: true, }, { name: "spokenNarration", // Narration text that will be read aloud during the presentation of the slide. type: "string", description: "The text to read while presenting the slide. Should be distinct from the slide's content, and can include additional context, references, etc. Will be read aloud as-is. Should be a few sentences long, clear, and smooth to read.", required: true, }, ], // The function to execute when the action is triggered. It creates a new slide with the provided details and appends it to the existing slides array. implementation: async (title, content, backgroundImageDescription, spokenNarration) => { const newSlide: SlideModel = { // Constructs the new slide object. title, content, backgroundImageDescription, spokenNarration, }; // Updates the slides state by appending the new slide to the end of the current slides array. setSlides((slides) => [...slides, newSlide]); }, }, [setSlides] // Dependency array for the hook. This action is dependent on the `setSlides` function, ensuring it reinitializes if `setSlides` changes. ); ``` 在上面的程式碼下方,定義一個名為`context`的變數,該變數使用名為`useCopilotContext`的自訂掛鉤從 copilot 上下文中檢索當前上下文。 ``` const context = useCopilotContext(); ``` 之後,定義一個名為`generateSlideTask`的函數,它包含一個名為`CopilotTask`的類別。 `CopilotTask`類別定義用於產生與簡報的整體主題相關的新投影片的指令 ``` const generateSlideTask = new CopilotTask({ instructions: "Make the next slide related to the overall topic of the presentation. It will be inserted after the current slide. Do NOT carry any research", }); ``` 然後在上面的程式碼下面初始化一個名為`generateSlideTaskRunning`的狀態變數,預設值為false。 ``` const [generateSlideTaskRunning, **setGenerateSlideTaskRunning**] = useState(false); ``` 之後,使用下面的程式碼更新簡報元件中的操作按鈕,以透過新增、刪除和導覽投影片來新增動態互動。 ``` // The JSX structure for the Presentation component. return ( <div className="relative"> {/* Renders the current slide using a Slide component with props for the slide data and a method to update it. */} <Slide slide={currentSlide} partialUpdateSlide={updateCurrentSlide} /> {/* Container for action buttons positioned at the top left corner of the relative parent */} <div className="absolute top-0 left-0 mt-6 ml-4 z-30"> {/* ActionButton to add a new slide. It is disabled when a generateSlideTask is running to prevent concurrent modifications. */} <ActionButton disabled={generateSlideTaskRunning} onClick={() => { const newSlide: SlideModel = { title: "Title", content: "Body", backgroundImageDescription: "random", spokenNarration: "The speaker's notes for this slide.", }; // Inserts the new slide immediately after the current slide and updates the slide index to point to the new slide. setSlides((slides) => [ ...slides.slice(0, currentSlideIndex + 1), newSlide, ...slides.slice(currentSlideIndex + 1), ]); setCurrentSlideIndex((i) => i + 1); }} className="rounded-r-none" > <PlusIcon className="h-6 w-6" /> </ActionButton> {/* ActionButton to generate a new slide based on the current context, also disabled during task running. */} <ActionButton disabled={generateSlideTaskRunning} onClick={async () => { setGenerateSlideTaskRunning(true); // Indicates the task is starting. await generateSlideTask.run(context); // Executes the task with the current context. setGenerateSlideTaskRunning(false); // Resets the flag when the task is complete. }} className="rounded-l-none ml-[1px]" > <SparklesIcon className="h-6 w-6" /> </ActionButton> </div> {/* Container for action buttons at the top right, including deleting the current slide and potentially other actions. */} <div className="absolute top-0 right-0 mt-6 mr-24"> {/* ActionButton for deleting the current slide, disabled if a task is running or only one slide remains. */} <ActionButton disabled={generateSlideTaskRunning || slides.length === 1} onClick={() => { console.log("delete slide"); // Removes the current slide and resets the index to the beginning as a simple handling strategy. setSlides((slides) => [ ...slides.slice(0, currentSlideIndex), ...slides.slice(currentSlideIndex + 1), ]); setCurrentSlideIndex((i) => 0); }} className="ml-5 rounded-r-none" > <TrashIcon className="h-6 w-6" /> </ActionButton> </div> {/* Display showing the current slide index and the total number of slides. */} <div className="absolute bottom-0 right-0 mb-20 mx-24 text-xl" style={{ textShadow: "1px 1px 0 #ddd, -1px -1px 0 #ddd, 1px -1px 0 #ddd, -1px 1px 0 #ddd", }} > Slide {currentSlideIndex + 1} of {slides.length} </div> {/* Navigation buttons to move between slides, disabled based on the slide index or if a task is running. */} <div className="absolute bottom-0 right-0 mb-6 mx-24"> {/* Button to move to the previous slide, disabled if on the first slide or a task is running. */} <ActionButton className="rounded-r-none" disabled={generateSlideTaskRunning || currentSlideIndex === 0} onClick={() => { setCurrentSlideIndex((i) => i - 1); }} > <BackwardIcon className="h-6 w-6" /> </ActionButton> {/* Button to move to the next slide, disabled if on the last slide or a task is running. */} <ActionButton className="mr-[1px] rounded-l-none" disabled={generateSlideTaskRunning || currentSlideIndex + 1 === slides.length} onClick={async () => { setCurrentSlideIndex((i) => i + 1); }} > <ForwardIcon className="h-6 w-6" /> </ActionButton> </div> </div> ); ``` 現在讓我們轉到`/[root]/src/app/page.tsx`文件,使用下面的程式碼匯入 CopilotKit 前端包和文件頂部的樣式。 ``` import { CopilotKit, } from "@copilotkit/react-core"; import { CopilotSidebar } from "@copilotkit/react-ui"; import "@copilotkit/react-ui/styles.css"; import "@copilotkit/react-textarea/styles.css"; ``` 然後使用`CopilotKit`和`CopilotSidebar`來包裝Presentation元件,如下所示。 ``` export default function AIPresentation() { return ( <CopilotKit url="/api/copilotkit/"> <CopilotSidebar instructions="Help the user create and edit a powerpoint-style presentation. IMPORTANT NOTE: SOMETIMES you may want to research a topic, before taking further action. BUT FIRST ASK THE USER if they would like you to research it. If they answer 'no', do your best WITHOUT researching the topic first." defaultOpen={true} labels={{ title: "Presentation Copilot", initial: "Hi you! 👋 I can help you create a presentation on any topic.", }} clickOutsideToClose={false} > <Presentation /> </CopilotSidebar> </CopilotKit> ); } ``` 之後,執行開發伺服器並導航到 http://localhost:3000/。您應該會看到應用程式內聊天機器人已整合到 PowerPoint Web 應用中。 ![應用程式內聊天機器人](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rb2g54qslrrfxyx2pbcy.png) 最後,給右側的聊天機器人一個提示,例如“在 JavaScript 上建立 PowerPoint 簡報”,聊天機器人將開始產生回應,完成後,使用底部的前進按鈕瀏覽產生的幻燈片。 注意:如果聊天機器人沒有立即產生投影片,請根據其回應給予適當的後續提示。 ![PowerPoint簡報](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/v6dl4av0asoeokzopwra.png) 結論 -- 總而言之,您可以使用 CopilotKit 建立應用內 AI 聊天機器人,該機器人可以查看當前應用程式狀態並在應用程式內執行操作。 AI 聊天機器人可以與您的應用程式前端、後端和第三方服務對話。 完整的原始碼:https://github.com/TheGreatBonnie/aipoweredpowerpointapp --- 原文出處:https://dev.to/copilotkit/how-to-build-an-ai-powered-powerpoint-generator-langchain-copilotkit-openai-nextjs-4c76

Snake...純 HTML⁉️ [沒有 JS,沒有 CSS,沒有圖片!!] 😱

他們說有些人就是喜歡混亂。 大家好👋🏼,我是格雷厄姆「喜歡混亂」TheDev,這次我帶著另一個愚蠢的網路實驗回來了(如果你願意,你可以[直接跳到遊戲](#the-game))。 一切都是那麼天真地開始,「我可以寫一個貪吃蛇遊戲嗎?」。 但是,一如既往,我肩膀上的小惡魔低聲說「讓它變得更難」......所以我想「沒有 JavaScript,用純 CSS 來做」。 他再次嘰嘰喳喳地說:「噗,還是太簡單了,而且你最近做了太多 CSS 東西,用原始的、無樣式的 HTML 來做吧」。 我轉向另一邊肩膀,想聽聽天使的想法,希望得到更明智的結果。 然後我想起天使從來沒有在我身邊... 所以這就是,snake,純 HTML 格式(用一點 PHP 技巧來支援它)。 這是正確的! - 沒有 JavaScript - 沒有圖片 - 沒有CSS - 沒有 Cookie 不過,我想澄清一下(因為我不想被指責為點擊誘餌),我正在使用 PHP 渲染此 HTML。 雖然可以僅使用文件以純 HTML 形式完成此操作,無需後端語言,但它需要 640,345,228,142,352,307,046,244,325,015,114,448,670,890, 662,773,914,918,117,331,955,996,440,709,549,671,345,290,477,020,322,434,911,210,797,593,280,795,101, 545,372,667,251,627,877,890,009,349,763,765,710,326,350,331,533,965,349,868,386,831,339,352,024,373, 788,157,786,791,506,311,858,702,618,270,169,819,740,062,983,025,308,591,298,346,162,272,304,558,339, 520,759,611,505,302,236,086,810,433,297,255,194,852,674,432,232,438,669,948,422,404,232,599,805,551,610,635,942,376,961,399 ,231,917,134,063,858,996,537,970,147,827,206,606,320,217,379,472,010,321,356,624,613,809,077,942,304,597,360,699,567,595,836, 096,158,715,129,913,822,286,578,579,549,361,617,654,480,453,222,007,825,818,400,848,436,415,591,229,454,275,384,803,558,374,5 18,022,675,900,061,399,560,145,595,206,127,211,192,918,105,032,491,008,000,000,000,000,000,000,000,000,000,000,000,000,000,00 0,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000 個文件。 所以請原諒使用 PHP 產生下一頁的「捷徑」(對於那些在技術 Twitter 上花費太多時間的人,也請原諒我使用「死」語言!😱🤣)。 不管怎樣,序言太多了,我知道你為什麼來這裡,你想看到它的實際效果! 玩 HTML 貪吃蛇(有警告!) ---------------- 在桌面 PC 上的 Chrome 上執行...對於我來說,在 Firefox 和 iOS 上的任何瀏覽器上執行速度太快...您將在本文後面了解原因。 所以基本上,在桌面版 Chrome 中玩吧! 關鍵是: - ALT + I向上, - ALT + J向左, - ALT + K向下, - ALT + L向右, - ALT + O開始新遊戲(一旦你輸了)。 在 Mac 上,我相信是Control + Option而不是Alt ! 如果你想知道為什麼奇怪的鍵而不是 WASD,不幸的是ALT + D已經在 Windows 上的 Chrome 中使用,所以我不得不選擇「安全」鍵。 **最後一個警告:**我們用於實現此功能的技巧之一會用大量 URL 淹沒您的瀏覽器歷史記錄...您已被警告! ### 遊戲 **遺憾的是,這無法在 codepen 中執行,因此您必須[在我的網站上玩 HTML Snake](https://grahamthe.dev/demos/snake/) 。** 當你玩完後,回來看看我用了什麼技巧來完成這個工作(並在評論中分享你的最高分!)。 問題 1:取得遊戲勾選 ----------- 對於遊戲,您*通常*需要有一個“遊戲勾選”。每個刻度是當一個動作發生或您計算一個新的遊戲狀態然後渲染新的遊戲狀態。 但這提出了我們的第一個問題,我們如何能夠在沒有 JavaScript 的情況下自動更新頁面? 嗯,在 HTML 中執行此操作實際上非常簡單,我們只需將[`<meta http-equiv="refresh"`](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/meta#http-equiv)設為較低值即可。 因此,我們從 0.35 秒刷新時間開始,然後隨著您的分數攀升,將刷新時間加快至 0.2 秒。 「元刷新」允許我們做的是指示瀏覽器載入頁面的 HTML 後,等待 X 秒,然後載入另一個 URL。 透過設定較低的刷新時間,然後更改我們在每次刷新時重定向到的 URL(稍後會詳細介紹),我們有一種方法可以讓頁面自行更改,即使您不按任何按鈕! 以下是格式的簡單範例: ``` <meta http-equiv="refresh" content="[time];url=[url-to-redirect-to]"> ``` **附註:**這是我之前提到的它不適用於其他瀏覽器的地方。他們不排除部分第二次刷新時間,因此刷新是即時的,使得遊戲太快而無法玩。 但僅元刷新不足以使遊戲正常執行,我們需要某種方法來保存遊戲狀態並將蛇方向的變化傳達給伺服器。 為此,我們使用另一個直接的技巧:URL 編碼的 GET 參數。 問題 2:管理遊戲狀態 ----------- 因為我們不能使用 POST 請求或類似的東西,所以我們需要另一個機制來管理瀏覽器和伺服器之間的遊戲狀態。 起初,我使用多個 GET 參數來管理狀態,因此 URL 如下所示: ``` url?playing=1&x=2&y=6&foodx=3&foody=6&dir=left. ``` 這一直工作得很好,直到我需要為蛇儲存多個點(它佔據的每個方塊的 x,y 座標)。 雖然我確實讓它與一些 hacky x,y 座標列表和解析一起工作(例如`snake=1,1,2,1` ,蛇位於x=1,y=1 和x=2,y=1),但這是凌亂的。 因此,我們轉向我們的好朋友: [`urlencode()`](https://www.php.net/manual/en/function.urlencode.php)和[`json_encode()`](https://www.php.net/manual/en/function.json-encode.php) 。 一起使用時,我可以取得一個陣列(或在本例中為多維陣列),將其轉換為 JSON,然後將其轉換為 URL 的有效字元。 讓我解釋: ### 在 URL 中儲存複雜資料 以下是我用於遊戲狀態的資料範例: ``` $state = array( 'width' => $width, 'height' => $height, 'snake' => array(array('x' => 5, 'y' => 5)), 'food' => array('x' => 7, 'y' => 7), 'direction' => 'right', 'score' => 0, 'state' => true ); ``` 要將這些資料儲存在 URL 中,我們可以使用以下命令: ``` $url = urlencode(json_encode($state)); ``` 透過 JSON 編碼我們的陣列,然後用 URL 友好的字符替換無效字符,這以 URL 友好(儘管不是人類友好!)的方式為我們提供了狀態: ``` %7B%22width%22%3A20%2C%22height%22%3A20%2C%22snake%22%3A%5B%7B%22x%22%3A19%2C%22y%22%3A5%7D%5D%2C%22food%22%3A%7B%22x%22%3A4%2C%22y%22%3A11%7D%2C%22direction%22%3A%22right%22%2C%22score%22%3A0%2C%22state%22%3Afalse%7D ``` 現在我們有一個機制可以將遊戲狀態傳遞到瀏覽器並備份到伺服器。 ### 最大 URL 長度 那些了解自己的東西的人會知道這裡有一個問題。 URL 長度有最大限制! 在 Chrome 中是 2083 個字元。 如果您玩遊戲的時間足夠長,您實際上會達到字元限制,因為為了儲存 x,y 位置對,我們每次使用超過 10 個字元。 但這是一個愚蠢的演示,所以我只想說:讓我知道如果你讓你的蛇足夠長,會發生什麼錯誤! 哦,在現實世界中,**您不應該對 URL 中的參數進行 JSON 編碼**,我們就這樣吧! 我們有狀態和遊戲標記,現在怎麼辦? ----------------- 這就對了! 嗯,差不多了。 我們需要將按鍵資訊傳達給伺服器。 ### 問題3:改變蛇的方向 這是最後一個問題(也是我們最終在 URL 中顯示遊戲狀態的原因),我們需要向伺服器傳達按鍵訊息以更改蛇的方向。 #### 問題 3a:按下按鈕 在我們將按鍵傳達給伺服器之前,我們需要某種方法來實際捕獲它們。 請記住,我們沒有 JS 來捕獲按鍵操作。 我們也不能使用`<button>`元素,因為它們需要 JS 才能運作。 所以我們剩下的就是不起眼的錨元素( `<a>` )。 但讓某人點擊錨點會讓遊戲變得很難玩。 幸運的是,HTML 中內建了一種名為[`accesskey`的](https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/accesskey)東西。 它們允許我們將一個字元指派給一個錨點,然後可以透過捷徑(ALT + Windows 上 Chrome 中的字元)存取這些字元。 這為我們提供了允許鍵盤控制的機制,我們只需要 4 個具有不同方向的連結(錨點)作為 URL,然後為每個連結分配一個`accesskey` 。 **重要提示:**應謹慎使用`accesskey` ,如果您選擇輔助科技 (AT) 使用者使用的按鍵,則可能會產生幹擾。 #### 問題 3b:方向 現在我們有了一種按鍵方法,以及一種將按鍵操作傳達給伺服器的方法,我們需要一種方法來管理按鍵操作,以便它們更新蛇的方向。 幸運的是,我們透過 URL 傳遞的狀態物件中已經有了一個`direction`屬性。 因此,我們要做的就是建立 4 個不同的 URL,每個方向一個。然後我們將這些加入到連結中就完成了。 ``` $encodedState = urlencode(json_encode($state)); <a href="index.php?state=<?php echo $encodedState; ?>&direction=up" accesskey="i">up (ALT + I)</a><br/> <a href="index.php?state=<?php echo $encodedState; ?>&direction=left" accesskey="j">left (ALT + J)</a> <a href="index.php?state=<?php echo $encodedState; ?>&direction=right" accesskey="l">right (ALT + L)</a> <a href="index.php?state=<?php echo $encodedState; ?>&direction=down" accesskey="k">down (ALT + K)</a> ``` 現在,例如,當您按ALT + K時,將單擊第四個連結,我們將當前狀態+新方向發送到伺服器! 現在剩下的就是獲取該資訊併計算下一個遊戲狀態。 ### 遊戲邏輯 最後,謎題的最後一部分是一些遊戲邏輯。 例如,在生成食物位置時,我們需要檢查它是否不在蛇已經佔據的圖塊上,因此我們有以下函數: ``` function generateFoodPosition($width, $height, $snake) { do { $food = array( 'x' => rand(0, $width - 1), 'y' => rand(0, $height - 1)); } while ( in_array($food, $snake) ); return $food; } ``` 還有一個移動蛇的功能 ``` function moveSnake($state) { $newHead = array('x' => $state['snake'][0]['x'], 'y' => $state['snake'][0]['y']); // Update snake's head position based on direction switch ($state['direction']) { case 'up': $newHead['y']--; break; case 'down': $newHead['y']++; break; case 'left': $newHead['x']--; break; case 'right': $newHead['x']++; break; } // Check if snake has collided with the wall or itself if ($newHead['x'] < 0 || $newHead['x'] >= $state['width'] || $newHead['y'] < 0 || $newHead['y'] >= $state['height'] || in_array($newHead, array_slice($state['snake'], 1))) { $state['state'] = false; return $state; // Game over } // Check if snake has eaten the food if ($newHead['x'] == $state['food']['x'] && $newHead['y'] == $state['food']['y']) { $state['score'] += 10; // Generate new food position $state['food'] = generateFoodPosition($state['width'], $state['height'], $state['snake']); } else { // Remove tail segment array_pop($state['snake']); } // Move snake array_unshift($state['snake'], $newHead); return $state; } ``` 以及建構遊戲板的循環。 ``` for ($y = 0; $y < 20; $y++) { echo "\r\n"; for ($x = 0; $x < 20; $x++) { if ($x == $state['food']['x'] && $y == $state['food']['y']) { echo '🍎'; } elseif (in_array(array('x' => $x, 'y' => $y), $state['snake'])) { echo '🟩'; }else{ echo '⬜'; } } } ``` 但我不會詳細介紹這些內容,因為您可以輕鬆找到(並找到更簡潔的方法)、找到其他人編寫的(更好的)程式碼並適應您的需求。 這是一個包裝 ------ 現在你已經知道了,我們使用元刷新、存取鍵和在 URL 中編碼複雜資料的技巧建立了一個遊戲。 這些東西對你的日常生活有用嗎?不,可能不會。 他們是否會在一個奇怪的邊緣情況下拯救你的屁股,完成這個工作,有能力使用黑客來交付產品情況?可能吧。 什麼?您沒想到我會提供您有用的教學嗎?你現在應該更清楚了。 但是,話雖如此,如果您確實喜歡這篇文章,或者奇蹟般地學到了一些新東西,請在下面給我留言,這真的意義重大! 祝大家週末愉快! 💗 --- 原文出處:https://dev.to/grahamthedev/snakein-pure-html-no-js-no-css-no-images-2ccg

html/css 小分享:設定複選框和開關的樣式

我可能不是唯一一個對瀏覽器的預設`<input type="checkbox">`感到沮喪的開發人員。 首先:**它不可擴展。**在此範例中,字體大小已縮放至`200%` ,但複選框仍保持其根大小,即`13.333333px` : ![預設複選框](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/delpw47gyetj091jeun0.png) 在本教程中,我們將剖析瀏覽器的預設複選框,看看是否可以做得更好。 --- 首先,我們需要使用`appearance:none`清除預設樣式並設定初始大小 - 這將是一個相對單位`em` : ``` [type=checkbox] { appearance: none; aspect-ratio: 1; box-sizing: border-box; font-size: 1em; width: 1em; } ``` `background-color`應該適應深色模式,因此我們將檢查它是否與任何[系統顏色](https://developer.mozilla.org/en-US/docs/Web/CSS/system-color)相符。它似乎與`Field`系統顏色匹配,所以讓我們使用它。 對於 Chrome 中的邊框顏色,它與系統顏色`ButtonBorder`匹配,但由於 Safari 使用*更輕的*`ButtonBorder` ,我們將使用適用於兩種瀏覽器的`GrayCanvas` 。 我們將加入一些 CSS 自訂屬性,稍後我們將使用它們來建立變體。 對於`border-radius`和`margin` ,我們將使用預設值,但將它們轉換為相對單位`em` 。 `border-width`似乎使用以下公式進行縮放: ``` (4/3) / root size ``` 由於根大小為`13.333333px` ,我們現在有: ``` [type=checkbox] { --_bdw: calc(1em * (4/3) / 13.333333); appearance: none; aspect-ratio: 1; background: var(--_bg, Field); border: var(--_bdw) solid var(--_bdc, GrayText); border-radius: var(--_bdrs, .2em); box-sizing: border-box; font-size: 1em; margin: var(--_m, .1875em .1875em .1875em .25em); position: relative; width: 1em; } ``` 讓我們看看它是否可擴展: ![可擴充複選框](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/dp6npvshq378jt0yk8o6.png) 好的!深色模式呢? ![深色模式](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/lm0aq2eixhf9or4ho67a.png) 這就是為什麼我**喜歡**系統顏色!接下來,讓我們新增瀏覽器在**未選取的**複選框上使用的相同懸停效果。 我們將混合`CanvasText` ,它在淺色模式下為黑色,在深色模式下為白色,並簡單地更新我們在上一步中加入的`--_bdc`屬性: ``` @media (hover: hover) { &:not(:checked):hover { --_bdc: color-mix(in srgb, GrayText 60%, CanvasText 40%); } } ``` --- 複選標記 ---- 現在是複選標記。我們**可以**在`::after`元素中使用旋轉的 CSS 方塊來做到這一點: ``` [type=checkbox]::after { border-color: GrayText; border-style: solid; border-width: 0 0.15em 0.15em 0; box-sizing: border-box; content: ''; aspect-ratio: 1 / 1.8; rotate: 40deg; width: 0.375em; } ``` ![CSS 中的複選標記](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/56ff7lvbtsljaxtoyt3h.png) 雖然這工作得很好,但我更喜歡在蒙版中使用 SVG,因為它更靈活。為此,我們將為遮罩加入一個屬性,並為`::after`元素的背景加入另一個`--_bga` ,該屬性將是複選標記的**顏色**。 ``` [role=checkbox] { --_bga: Field; --_mask: url('data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" stroke-width="3" stroke="%23000" fill="none" stroke-linecap="round" stroke-linejoin="round"> <path d="M5 12l5 5l10 -10"/></svg>'); &::after { background: var(--_bga, transparent); content: ""; inset: 0; position: absolute; mask: var(--_mask) no-repeat center / contain; -webkit-mask: var(--_mask) no-repeat center / contain; } } ``` 所以,我們現在**確實**有一個複選標記,只是看不到它,因為蒙版顏色設定為`transparent` 。 讓我們使用`:checked` -state 更新點擊時複選框的顏色。但在此之前,我們需要先弄清楚**哪種**顏色! Safari 是唯一支援系統顏色`AccentColor`瀏覽器,因此我們需要為此建立自己的變數`--_accent` ,在 Mac 上對應於`#0075ff` : ``` [type=checkbox] { --_accent: #0075ff; &:checked { --_bdc: transparent; --_bg: var(--_accent); --_bga: Field; } } ``` 讓我們看看我們建構了什麼: ![複選框樣式](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9l3tzwwqkmrr4bpzrg19.png) 還有深色模式?我們需要先更新`--_accent`屬性,因為`AccentColor`尚未在所有瀏覽器中運作: ``` @media (prefers-color-scheme: dark) { --_accent: #99C8FF; } ``` 讓我們檢查: ![複選框深色模式](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0kuid7fnr3obftfjr85s.png) 涼爽的!現在我們需要加入的是`:checked:hover` -state,它類似於我們之前新增的 border-hover: ``` @media (hover: hover) { &:checked:hover { --_bg: color-mix(in srgb, var(--_accent) 60%, CanvasText 40%); } } ``` 讓我們比較一下它在 Chrome、Safari 和 Firefox 中的外觀: ![瀏覽器比較](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/hi9qej87nns2wjd4jqiw.png) 看來我們通過考驗了! --- 變體 -- 建立變體非常簡單:您只需要更新一些屬性。例子: ``` .rounded { --_bdrs: 50%; } .square { --_bdrs: 0; } ``` 然後在 HTML 中: ``` <input type="checkbox" class="rounded"> <input type="checkbox" class="square"> ``` ![變體](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vu5g82hu5zv65izekwsn.png) — 或全力以赴並建立*老式*複選框: ![老派複選框](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ngan912ja853wx4q8gil.png) > **關於圓形複選框的註釋:**這是*不好的*做法,正如您可以在[這篇精彩的文章](https://tonsky.me/blog/checkbox/)中讀到的那樣。不過,也有一些例外,例如這個「影像選擇器」: ![圓形影像選擇](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j36lzrpf7sxvimocpoud.png) 開關 -- 對於開關,我們將加入一個`role="switch"` ,所以它是: ``` <input type="checkbox" role="switch"> ``` 蘋果最近加入了[自己的 switch-control](https://dev.to/madsstoumann/a-first-look-at-apples-new-switch-control-3pnd) ,但`role="switch"`是跨瀏覽器的。同樣,我們只需要更新我們之前建立的許多屬性: ``` [role=switch] { --_bdc--hover: transparent; --_bdrs: 1em; --_bg: #d1d1d1; --_bga: Field; --_mask: none; aspect-ratio: 1.8 / 1; border: 0; display: grid; padding: .125em; place-content: center start; width: 1.8em; &::after { border-radius: 50%; height: .75em; inset: unset; position: static; width: .75em; } &:checked { --_bg: var(--_bg--checked, var(--_accent)); justify-content: end; } } ``` 這給了我們: ![開關](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2rlfyayxyzkqcr78qovn.png) --- 示範 -- 就是這樣!下面是帶有演示的 Codepen: https://codepen.io/stoumann/pen/OJqQNgm --- 駭客與縫合 ----- 以下是我在 Codepen 上使用複選框所做的一系列工作: ### 複選框電影院 選擇座位。還可以修改為在火車、飛機上選擇座位...... https://codepen.io/stoumann/pen/eYXpEBa ### 天際線複選框 點擊窗戶打開公寓裡的燈… https://codepen.io/stoumann/pen/KKbGJqd ### 按數字繪畫 先選擇一種顏色(使用`<input type="radio">` ),然後按一下對應的數字(複選框)... https://codepen.io/stoumann/pen/VwRejpR ### 點對點 不需要 JavaScript,但我把它留在那裡供你玩… https://codepen.io/stoumann/pen/zYbNRNL ### 來自地獄的條款和條件 檢查全部… https://codepen.io/stoumann/pen/GRwRjYP --- 每日 toggle ---- Alvaro Montoro 正在建立大量開關/撥動開關 - 2024 年每天一個。請[在此處](https://codepen.io/collection/aMPYMo)查看。 --- 原文出處:https://dev.to/madsstoumann/styling-checkboxes-and-switches-pf0

30 個 JavaScript 奇妙小技巧

歡迎使用我們精選的 JavaScript 技巧集合,它將幫助您優化程式碼、使其更具可讀性並節省您的時間。 讓我們深入研究 JavaScript 的功能和超越傳統的技巧,並發現這種強大的程式語言的全部潛力。 ### 1. 使用!!轉換為布林值 使用雙重否定快速將任何值轉換為布林值。 ``` let truthyValue = !!1; // true let falsyValue = !!0; // false ``` ### 2. 預設功能參數 設定函數參數的預設值以避免未定義的錯誤。 ``` function greet(name = "Guest") { return `Hello, ${name}!`; } ``` ### 3. 短 if-else 的三元運算符 `if-else`語句的簡寫。 ``` let price = 100; let message = price > 50 ? "Expensive" : "Cheap"; ``` ### 4. 動態字串的範本文字 使用模板文字在字串中嵌入表達式。 ``` let item = "coffee"; let price = 15; console.log(`One ${item} costs $${price}.`); ``` ### 5. 解構賦值 輕鬆從物件或陣列中提取屬性。 ``` let [x, y] = [1, 2]; let {name, age} = {name: "Alice", age: 30}; ``` ### 6. 用於陣列和物件克隆的擴展運算符 克隆陣列或物件而不引用原始陣列或物件。 ``` let originalArray = [1, 2, 3]; let clonedArray = [...originalArray]; ``` ### 7. 短路評估 使用邏輯運算子進行條件執行。 ``` let isValid = true; isValid && console.log("Valid!"); ``` ### 8. 可選連結 (?.) 如果引用為`nullish`則可以安全地存取巢狀物件屬性,而不會出現錯誤。 ``` let user = {name: "John", address: {city: "New York"}}; console.log(user?.address?.city); // "New York" ``` ### 9. 空合併運算子 (??) 使用`??`為`null`或`undefined`提供預設值。 ``` let username = null; console.log(username ?? "Guest"); // "Guest" ``` [![monday.com 的互動式橫幅展示了在數位介面上組織工作流程任務的雙手,並帶有「告訴我如何做」號召性用語按鈕。](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xd7qdmxdd726kskelydk.png)](https://try.monday.com/9xf9ftaa4i2f) ### 10. 使用`map` 、 `filter`和`reduce`進行陣列操作 無需傳統循環即可處理陣列的優雅方法。 ``` // Map let numbers = [1, 2, 3, 4]; let doubled = numbers.map(x => x * 2); // Filter const evens = numbers.filter(x => x % 2 === 0); // Reduce const sum = numbers.reduce((accumulator, currentValue) => accumulator + currentValue, 0); ``` ### 11.標記模板文字 使用模板文字進行函數呼叫以進行自訂字串處理。 ``` function highlight(strings, ...values) { return strings.reduce((prev, current, i) => `${prev}${current}${values[i] || ''}`, ''); } let price = 10; console.log(highlight`The price is ${price} dollars.`); ``` ### 12.使用Object.entries()和Object.fromEntries() 將物件轉換為陣列並返回以方便操作。 ``` let person = {name: "Alice", age: 25}; let entries = Object.entries(person); let newPerson = Object.fromEntries(entries); ``` ### 13. 唯一元素的集合物件 使用 Set 儲存任何類型的唯一值。 ``` let numbers = [1, 1, 2, 3, 4, 4]; let uniqueNumbers = [...new Set(numbers)]; ``` ### 14. 物件中的動態屬性名稱 在物件文字表示法中使用方括號來建立動態屬性名稱。 ``` let dynamicKey = 'name'; let person = {[dynamicKey]: "Alice"}; ``` ### 15. 使用bind()進行函數柯里化 建立一個新函數,在呼叫時將其 this 關鍵字設定為提供的值。 ``` function multiply(a, b) { return a * b; } let double = multiply.bind(null, 2); console.log(double(5)); // 10 ``` ### 16. 使用 Array.from() 從類別陣列物件建立陣列 將類似陣列或可迭代的物件轉換為真正的陣列。 ``` let nodeList = document.querySelectorAll('div'); let nodeArray = Array.from(nodeList); ``` ### 17. 可迭代物件的 for...of 循環 直接迭代可迭代物件(包括陣列、映射、集合等)。 ``` for (let value of ['a', 'b', 'c']) { console.log(value); } ``` ### 18. 使用 Promise.all() 實作並發 Promise 同時執行多個 Promise 並等待所有的都解決。 ``` let promises = [fetch(url1), fetch(url2)]; Promise.all(promises) .then(responses => console.log('All done')); ``` ### 19. 函數參數的剩餘參數 將任意數量的參數捕獲到陣列中。 ``` function sum(...nums) { return nums.reduce((acc, current) => acc + current, 0); } ``` [![Coursera Plus 訂閱產品包括 AWS 基礎、Google IT 支援專業憑證和商業網路安全專業化。](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ys5gk2tfzcn4iniuq48s.png)](https://imp.i384100.net/c/3922519/1320997/14726) ### 20. 用於性能優化的記憶 儲存函數結果以避免冗餘處理。 ``` const memoize = (fn) => { const cache = {}; return (...args) => { let n = args[0]; // assuming single argument for simplicity if (n in cache) { console.log('Fetching from cache'); return cache[n]; } else { console.log('Calculating result'); let result = fn(n); cache[n] = result; return result; } }; }; ``` ### 21. 使用 ^ 交換值 使用 XOR 以位元運算子交換兩個變數的值,無需使用臨時變數。 ``` let a = 1, b = 2; a ^= b; b ^= a; a ^= b; // a = 2, b = 1 ``` ### 22. 使用 flat() 展平陣列 使用`flat()`方法輕鬆展平巢狀陣列,並將展平深度作為可選參數。 ``` let nestedArray = [1, [2, [3, [4]]]]; let flatArray = nestedArray.flat(Infinity); ``` ### 23. 用一元加法轉換為數字 使用一元加運算子快速將字串或其他值轉換為數字。 ``` let str = "123"; let num = +str; // 123 as a number ``` ### 24. HTML 片段的模板字串 使用模板字串建立 HTML 片段,使動態 HTML 生成更加清晰。 ``` let items = ['apple', 'orange', 'banana']; let html = `<ul>${items.map(item => `<li>${item}</li>`).join('')}</ul>`; ``` ### 25. 使用 Object.assign() 合併物件 將多個來源物件合併到一個目標物件中,有效地組合它們的屬性。 ``` let obj1 = { a: 1 }, obj2 = { b: 2 }; let merged = Object.assign({}, obj1, obj2); ``` [![符合人體工學的垂直滑鼠旨在減輕手腕壓力](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/56c0z4lzxtkthnnk8gsb.jpg)](https://amzn.to/3UXGIyx) 使用符合人體工學的滑鼠優化您的編程設置,專為舒適和長時間的編碼會話而定制。 ### 26. 預設值短路 處理潛在的未定義或空變數時,使用邏輯運算子指派預設值。 ``` let options = userOptions || defaultOptions; ``` ### 27. 使用括號表示法動態存取物件屬性 使用括號表示法動態存取物件的屬性,當屬性名稱儲存在變數中時非常有用。 ``` let property = "name"; let value = person[property]; // Equivalent to person.name ``` ### 28. 使用 Array.includes() 進行存在檢查 使用includes() 檢查陣列是否包含某個值,它是indexOf 的更清晰的替代方法。 ``` if (myArray.includes("value")) { // Do something } ``` ### 29. Function.prototype.bind() 的強大功能 將函數綁定到上下文(此值)並部分套用參數,以建立更多可重複使用和模組化的程式碼。 ``` const greet = function(greeting, punctuation) { return `${greeting}, ${this.name}${punctuation}`; }; const greetJohn = greet.bind({name: 'John'}, 'Hello'); console.log(greetJohn('!')); // "Hello, John!" ``` ### 30.防止物件修改 使用`Object.freeze()`防止物件進行修改,使其不可變。對於更深層的不變性,請考慮更徹底地強制不變性的函式庫。 ``` let obj = { name: "Immutable" }; Object.freeze(obj); obj.name = "Mutable"; // Fails silently in non-strict mode ``` 我希望這些 JavaScript 技巧為您提供如何進行[JavaScript 程式設計的](https://www.w3schools.com/js/)新視角。 從利用模板文字的簡潔功能到掌握`map` 、 `filter`和`reduce`的效率,這些 JavaScript 技巧將豐富您的開發工作流程並激發您的下一個專案。 讓這些 JavaScript 技巧不僅可以完善您目前的專案,還可以在您的[程式設計之旅](https://www.webdevstory.com/programming-roadmap/)中激發未來創新的靈感。 ***支持我們的技術見解*** [![請我喝杯咖啡](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/lsm9uucbnw7x9iw0loxr.png)](https://www.buymeacoffee.com/mmainulhasan) [![透過 PayPal 按鈕捐贈](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ipnhbim2ba56kt32zhn3.png)](https://www.paypal.com/donate/?hosted_button_id=GDUQRAJZM3UR8) 注意:此頁面上的某些連結可能是附屬連結。如果您透過這些連結進行購買,我可能會賺取少量佣金,而無需您支付額外費用。感謝您的支持! --- 原文出處:https://dev.to/mmainulhasan/30-javascript-tricky-hacks-gfc

為所有正規表示式討厭者(和愛好者)準備的正規表示式備忘錄👀

我使用正規表示式的經驗 =========== 我一直遠離正規表示式。在我第一年的電腦科學實驗室中,有一個涉及正規表示式的練習。我想那是我第一次被介紹給它。我當時認為這很酷,但看起來太難了,所以我一直在避免它,或者只是在谷歌上搜尋如何解決某個正規表示式問題。但我*終於*花了一些時間來正確學習它🎉 ![](https://media.giphy.com/media/czoS1CAP2YZBS/giphy.gif) 在閱讀了一些資源並涉獵之後,可以肯定地說我不再害怕正規表示式了!我發現自己在我所做的許多編碼練習中都使用了它。所需要的只是練習!以下是我根據我學到的正規表示式和我使用的資源編寫的備忘單(帶有範例) 備忘錄 === 我已經包含了一些我學到的 Javascript 中不可用的正規表示式。對於這些,我都註解掉了。如果需要的話請記住「g」修飾符!對於我的範例,我省略了修飾符。 ``` let regex; /* matching a specific string */ regex = /hello/; // looks for the string between the forward slashes (case-sensitive)... matches "hello", "hello123", "123hello123", "123hello"; doesn't match for "hell0", "Hello" regex = /hello/i; // looks for the string between the forward slashes (case-insensitive)... matches "hello", "HelLo", "123HelLO" regex = /hello/g; // looks for multiple occurrences of string between the forward slashes... /* wildcards */ regex = /h.llo/; // the "." matches any one character other than a new line character... matches "hello", "hallo" but not "h\nllo" regex = /h.*llo/; // the "*" matches any character(s) zero or more times... matches "hello", "heeeeeello", "hllo", "hwarwareallo" /* shorthand character classes */ regex = /\d/; // matches any digit regex = /\D/; // matches any non-digit regex = /\w/; // matches any word character (a-z, A-Z, 0-9, _) regex = /\W/; // matches any non-word character regex = /\s/; // matches any white space character (\r (carriage return),\n (new line), \t (tab), \f (form feed)) regex = /\S/; // matches any non-white space character /* specific characters */ regex = /[aeiou]/; // matches any character in square brackets regex = /[ck]atherine/; // matches catherine or katherine regex = /[^aeiou]/; // matches anything except the characters in square brackets /* character ranges */ regex = /[a-z]/; // matches all lowercase letters regex = /[A-Z]/; // matches all uppercase letters regex = /[e-l]/; // matches lowercase letters e to l (inclusive) regex = /[F-P]/; // matches all uppercase letters F to P (inclusive) regex = /[0-9]/; // matches all digits regex = /[5-9]/; // matches any digit from 5 to 9 (inclusive) regex = /[a-zA-Z]/; // matches all lowercase and uppercase letters regex = /[^a-zA-Z]/; // matches non-letters /* matching repetitions using quantifiers */ regex = /(hello){4}/; // matches "hellohellohellohello" regex = /hello{3}/; // matches "hellooo" and "helloooo" but not "helloo" regex = /\d{3}/; // matches 3 digits ("312", "122", "111", "12312321" but not "12") regex = /\d{3,7}/; // matches digits that occur between 3 and 7 times (inclusive) regex = /\d{3,}/; // matches digits that occur at least 3 times /* matching repetitions using star and plus */ regex = /ab*c/; // matches zero or more repetitions of "b" (matches "abc", "abbbbc", "ac") regex = /ab+c/; // matches one or more repetitions of "b" (matches "abc", "abbbbc", but not "ac") /* matching beginning and end items */ regex = /^[A-Z]\w*/; // matches "H", "Hello", but not "hey" regex = /\w*s$/; // matches "cats", "dogs", "avocados", but not "javascript" /* matching word boundaries positions of word boundaries: 1. before the first character in string (if first character is a word character) 2. after the last character in the string, if the last character is a word character 3. between two characters in string, where one is a word character and the other isn't */ regex = /\bmeow\b/; // matches "hey meow lol", "hey:meow:lol", but not "heymeow lol" /* groups */ regex = /it is (ice )?cold outside/; // matches "it is ice cold outside" and "it is cold outside" regex = /it is (?:ice )?cold outside/; // same as above except it is a non-capturing group regex = /do (cats) like taco \1/; // matches "do cats like taco cats" regex = /do (cats) like (taco)\? do \2 \1 like you\?/; // matches "do cats like taco? do taco cats like you?" //branch reset group (available in Perl, PHP, R, Delphi... commented out because this is a js file) // regex = /(?|(cat)|(dog))\1/; // matches "catcat" and "dogdog" /* alternative matching */ regex = /i like (tacos|boba|guacamole)\./; // matches "i like tacos.", "i like boba.", and "i like guacamole." /* forward reference (available in Perl, PHP, Java, Ruby, etc... commented out because this is a js file) */ // regex = /(\2train|(choo))+/; // matches "choo", "choochoo", "chootrain", choochootrain", but not "train" /* lookaheads */ regex = /z(?=a)/; // positive lookahead... matches the "z" before the "a" in pizza" but not the first "z" regex = /z(?!a)/; // negative lookahead... matches the first "z" but not the "z" before the "a" /* lookbehinds */ regex = /(?<=[aeiou])\w/; // positive lookbehind... matches any word character that is preceded by a vowel regex = /(?<![aeiou])\w/; // negative lookbehind... matches any word character that is not preceded by a vowel /* functions I find useful */ regex.test("hello"); // returns true if found a match, false otherwise regex.exec("hello"); // returns result array, null otherwise "football".replace(/foot/,"basket"); // replaces matches with second argument ``` 感謝 Sarthak 建立了我的備忘錄的[GitHub 要點](https://gist.github.com/sarthology/b269c4ab81832c03f80eb48920f1abce),也感謝 Xian-an 將其翻譯成[中文](https://gist.github.com/cxa/901e1862cd9ddf5c721cea6f7807d77a)👏 資源 == - 「正規表示式」挑戰是[FreeCodeCamp](https://freecodecamp.org)上「Javascript 演算法和資料結構認證」的一部分 - [MDN 正規表示式文件](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions) - [正規表示式](https://regexone.com/) - [Regex101](https://regex101.com/)用於測試(您也可以使用 Chrome 開發者控制台) - [HackerRank](https://hackerrank.com/)正規表示式挑戰練習 ![](https://media.giphy.com/media/111ebonMs90YLu/giphy.gif) 就是這樣,夥計們!希望這對您有幫助☺️ --- 原文出處:https://dev.to/catherinecodes/a-regex-cheatsheet-for-all-those-regex-haters-and-lovers--2cj1

JavaScript 中的 async 與 defer:哪個更好?🤔

大家好!我希望你一切都好。本文將探討一個有趣的 Javascript 主題。 `async`和`defer`是在 HTML 文件中包含外部 JavaScript 檔案時使用的屬性。它們會影響瀏覽器載入和執行腳本的方式。讓我們詳細了解一下它們。 預設行為 ---- 我們通常使用`<script>`標籤將 HTML 頁面與外部 javascript 連接。傳統上,JavaScript `<script>`標籤通常放置在 HTML 文件的`<head>`部分。然而,這樣做意味著 HTML 的解析會被阻止,直到 JavaScript 檔案被取得並執行為止,導致頁面載入時間變慢。如今,我們更喜歡在頁面的`<body>`元素的所有內容首先加載之後保留`<script>`標記。 ``` <script src="example.js"></script> ``` HTML 解析和腳本執行的過程如下 ![預設](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/8cvwth1dxa1gjtv7fa9d.png) 非同步 --- 當我們包含具有 async 屬性的腳本時,它會告訴瀏覽器在解析 HTML 文件時非同步下載腳本。腳本在背景下載,不會阻塞 HTML 解析過程。 下載腳本後,它會非同步執行,這意味著它可以隨時執行,甚至在 HTML 文件完成解析之前也可以執行。 ``` <script src="example.js" async></script> ``` 如果非同步載入多個腳本,它們將在下載完成後立即執行,無論它們在文件中的順序如何。當腳本不依賴完全載入的 DOM 或其他腳本時,它非常有用。 ![非同步](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rdc0ui3yp1rnbag7psgr.png) 延遲 -- 當我們包含具有 defer 屬性的腳本時,它也會告訴瀏覽器在解析 HTML 文件時非同步下載腳本。 然而,腳本的執行被推遲到 HTML 文件被解析之後。 ``` <script src="example.js" defer></script> ``` 具有 defer 屬性的腳本將按照它們在文件中出現的順序執行。當腳本依賴完全解析的 DOM 或腳本執行順序很重要時,它非常有用。 ![延遲](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/uh5mo1x1pl3y3zpkgpeg.png) 結論 -- async 和 defer 都允許 HTML 解析過程繼續進行,而無需等待腳本下載。 差別在於腳本執行的時間: 使用非同步,腳本在下載後立即執行,可能在 HTML 文件完全解析之前執行。使用 defer,腳本僅在 HTML 文件完全解析之後、 `DOMContentLoaded`事件之前執行。 需要注意的重要事項之一是,只有當我們有可以獨立執行且不依賴 DOM 結構的腳本時,我們才應該使用 async,而當我們需要維護腳本執行順序或依賴 DOM 時,我們應該使用 defer結構。 我希望您喜歡這篇文章,如果您喜歡,請不要忘記按讚! 😃 **與我聯絡-** - [推特](https://twitter.com/fidalmathew10) - [github](https://github.com/FidalMathew) - [領英](https://www.linkedin.com/in/fidalmathew/) --- 原文出處:https://dev.to/fidalmathew/async-vs-defer-in-javascript-which-is-better-26gm

100 多個專案創意

**編輯**:大家好!在對本文做出驚人反應後,我建立了一個名為「每週專案俱樂部」的專案。每週您的收件匣都會收到需要解決的問題。你可以努力解決問題,並且你將得到整個俱樂部的幫助,讓你走上正軌。了解更多並[在這裡](https://weeklyproject.club)註冊! 有一天我注意到一個模式。我注意到很多人都在努力 學習編程,但他們心中沒有特定的目標。我已經討論過如何了解您想要學習程式設計的原因可以幫助您選擇要學習的語言[!](https://pickaframework.com/articles/why/) ,以及如何實際做出決定([在這裡!](https://pickaframework.com/feature_fishing/) )但是專案有什麼幫助呢? 當我指導程式設計師時,我發現有一個專案可以幫助排除其他一些幹擾,例如想知道你是否使用了正確的語言。透過專注於一個特定的目標,你就不用那麼費力去擔心*這*是否正是你應該使用的語言。結果是你建立了一些簡潔的東西,並且一路上你學到了一些東西! 2隻鳥,1塊石頭。 這就是為什麼我為初學者程式設計師策劃了這個專案清單。許多人列出了大量的專案來學習編程,但很少按照難度進行組織。我瀏覽了幾個流行的程式設計專案想法清單。如果您想查看完整列表,可以在頁面底部找到來源。 我將其分為教程和想法。教程包含資源連結,而想法只是專案的一般描述。我還列出了我最喜歡的初學者清單。 看看,看看是否有什麼啟發你! 教學 == 我的最愛 ---- - [透過 30 個教學在 30 天內建立 30 個東西](https://javascript30.com) - [在 30 分鐘內建立一個簡單的搜尋機器人](https://medium.freecodecamp.org/how-to-build-a-simple-search-bot-in-30-minutes-eb56fcedcdb1) - [使用 Xamarin 和 Visual Studio 建立 iOS 照片庫應用程式](https://www.raywenderlich.com/134049/building-ios-apps-with-xamarin-and-visual-studio) - [建立 Android 手電筒應用程式](https://www.youtube.com/watch?v=dhWL4DC7Krs)(影片) - [製作聊天應用程式](https://medium.freecodecamp.org/how-to-build-a-chat-application-using-react-redux-redux-saga-and-web-sockets-47423e4bc21a) - [使用 React Native 建立 ToDo 應用程式](https://blog.hasura.io/tutorial-fullstack-react-native-with-graphql-and-authentication-18183d13373a) 簡單的 --- - [使用 C# 和 Xamarin 建立空白應用程式(正在進行中)](https://www.intertech.com/Blog/xamarin-tutorial-part-1-create-a-blank-app/) - [使用 Xamarin 和 Visual Studio 建立 iOS 照片庫應用程式](https://www.raywenderlich.com/134049/building-ios-apps-with-xamarin-and-visual-studio) - [建立加載畫面](https://medium.freecodecamp.org/how-to-build-a-delightful-loading-screen-in-5-minutes-847991da509f) - [使用 JS 建立 HTML 計算器](https://medium.freecodecamp.org/how-to-build-an-html-calculator-app-from-scratch-using-javascript-4454b8714b98) - [建立 React Native Todo 應用程式](https://egghead.io/courses/build-a-react-native-todo-application) - 使用 Node.js 編寫 Twitter 機器人 ``` - [Part 1](https://codeburst.io/build-a-simple-twitter-bot-with-node-js-in-just-38-lines-of-code-ed92db9eb078) ``` ``` - [Part 2](https://codeburst.io/build-a-simple-twitter-bot-with-node-js-part-2-do-more-2ef1e039715d) ``` - [建立一個簡單的 RESTFUL Web 應用程式](https://closebrace.com/tutorials/2017-03-02/creating-a-simple-restful-web-app-with-nodejs-express-and-mongodb) - [在 30 分鐘內建立一個簡單的搜尋機器人](https://medium.freecodecamp.org/how-to-build-a-simple-search-bot-in-30-minutes-eb56fcedcdb1) - [建立一個工作抓取 Web 應用程式](https://medium.freecodecamp.org/how-i-built-a-job-scraping-web-app-using-node-js-and-indreed-7fbba124bbdc) - [使用 Python 挖掘 Twitter 資料](https://marcobonzanini.com/2015/03/02/mining-twitter-data-with-python-part-1/) - [使用 Scrapy 和 MongoDB 抓取網站](https://realpython.com/blog/python/web-scraping-with-scrapy-and-mongodb/) - [如何使用 Python 和 Selenium WebDriver 進行抓取](http://www.byperth.com/2018/04/25/guide-web-scraping-101-what-you-need-to-know-and-how-to-scrape-with-python-selenium-webdriver/) - [我應該使用 BeautifulSoup 觀看哪部電影](https://medium.com/@nishantsahoo.in/which-movie-should-i-watch-5c83a3c0f5b1) - [使用 Flask 建立微博](https://blog.miguelgrinberg.com/post/the-flask-mega-tutorial-part-i-hello-world) - 在 Django 中建立部落格 Web 應用程式 ``` - [Part I : Introduction](https://tutorial.djangogirls.org/en/) ``` ``` - [Part II : Extension To Add More Features](https://legacy.gitbook.com/book/djangogirls/django-girls-tutorial-extensions/details) ``` - [選擇您自己的冒險演示](https://www.twilio.com/blog/2015/03/choose-your-own-adventures-presentations-wizard-mode-part-1-of-3.html) - [使用 Flask 和 RethinkDB 建立待辦事項列表](https://realpython.com/blog/python/rethink-flask-a-simple-todo-list-powered-by-flask-and-rethinkdb/) 中等的 --- - [透過建立簡單的 RPG 遊戲來學習 C#](http://scottlilly.com/learn-c-by-building-a-simple-rpg-index/) - [用 C# 創作 Rogue-like 遊戲](https://roguesharp.wordpress.com/) - [使用 Clojure 建構 Twitter 機器人](http://howistart.org/posts/clojure/1/index.html) - [建立拼字檢查器](https://bernhardwenzel.com/articles/clojure-spellchecker/) - [使用 Java 建立簡單的 HTTP 伺服器](http://javarevisited.blogspot.com/2015/06/how-to-create-http-server-in-java-serversocket-example.html) - [建立 Android 手電筒應用程式](https://www.youtube.com/watch?v=dhWL4DC7Krs)(影片) - [建立具有使用者身份驗證的 Spring Boot 應用程式](https://scotch.io/tutorials/build-a-spring-boot-app-with-user-authentication) - [透過 30 個教學在 30 天內建立 30 個東西](https://javascript30.com) - [使用純 JS 建立應用程式](https://medium.com/codingthesmartway-com-blog/pure-javascript-building-a-real-world-application-from-scratch-5213591cfcd6) - [建立無伺服器 React.js 應用程式](http://serverless-stack.com/) - [建立 Trello 克隆](http://codeloveandboards.com/blog/2016/01/04/trello-tribute-with-phoenix-and-react-pt-1/) - [使用 React、Node、MongoDB 和 SocketIO 建立角色投票應用程式](http://sahatyalkabov.com/create-a-character-voting-app-using-react-nodejs-mongodb-and-socketio/) - [React 教學:克隆 Yelp](https://www.fullstackreact.com/articles/react-tutorial-cloning-yelp/) - [使用 React.js 和 Node.js 建立簡單的中型克隆](https://codeburst.io/build-simple-medium-com-on-node-js-and-react-js-a278c5192f47) - [在 JS 中整合 MailChimp](https://medium.freecodecamp.org/how-to-integrate-mailchimp-in-a-javascript-web-app-2a889fb43f6f) - [使用 React Native 建立 ToDo 應用程式](https://blog.hasura.io/tutorial-fullstack-react-native-with-graphql-and-authentication-18183d13373a) - [製作聊天應用程式](https://medium.freecodecamp.org/how-to-build-a-chat-application-using-react-redux-redux-saga-and-web-sockets-47423e4bc21a) - [使用 React Native 建立新聞應用程式](https://medium.freecodecamp.org/create-a-news-app-using-react-native-ced249263627) - [學習 React 的 Webpack](https://medium.freecodecamp.org/learn-webpack-for-react-a36d4cac5060) - [建立您自己的 React 樣板](https://medium.freecodecamp.org/how-to-build-your-own-react-boilerplate-2f8cbbeb9b3f) - [基本 React+Redux 入門教學](https://hackernoon.com/a-basic-react-redux-introductory-tutorial-adcc681eeb5e) - [建立一個預約安排程序](https://hackernoon.com/build-an-appointment-scheduler-using-react-twilio-and-cosmic-js-95377f6d1040) - 使用 Angular 2+ 建立具有離線功能的 Hacker News 用戶端 ``` - [Part 1](https://houssein.me/angular2-hacker-news) ``` ``` - [Part 2](https://houssein.me/progressive-angular-applications) ``` - 帶有 Angular 5 的 ToDo 應用程式 ``` - [Introduction to Angular](http://www.discoversdk.com/blog/intro-to-angular-and-the-evolution-of-the-web) ``` ``` - [Part 1](http://www.discoversdk.com/blog/angular-5-to-do-list-app-part-1) ``` - 帶有 Angular 5 的 ToDo 應用程式 ``` - [Introduction to Angular](http://www.discoversdk.com/blog/intro-to-angular-and-the-evolution-of-the-web) ``` ``` - [Part 1](http://www.discoversdk.com/blog/angular-5-to-do-list-app-part-1) ``` 難的 -- - [建構一個解釋器](http://www.craftinginterpreters.com/)(第 14 章是用 C 寫的) - [用 C 語言寫一個 Shell](https://brennan.io/2015/01/16/write-a-shell-in-c/) - [編寫 FUSE 文件系統](https://www.cs.nmsu.edu/~pfeiffer/fuse-tutorial/) - [建立您自己的文字編輯器](http://viewsourcecode.org/snaptoken/kilo/) - [建立自己的 Lisp](http://www.buildyourownlisp.com/) - [建構 CoreWiki](https://www.youtube.com/playlist?list=PLVMqA0_8O85yC78I4Xj7z48ES48IQBa7p)這是一個 Wiki 風格的內容管理系統,完全用 C# 使用 ASP.NET Core 和 Razor Pages 編寫。您可以[在這裡](https://github.com/csharpfritz/CoreWiki)找到原始程式碼。 - [建構 JIRA 與 Clojure 和 Atlassian Connect 的集成](https://hackernoon.com/building-a-jira-integration-with-clojure-atlassian-connect-506ebd112807) - [建構一個解釋器](http://www.craftinginterpreters.com/)(第 4-13 章是用 Java 寫的) - [使用 Mocha、React、Redux 和 Immutable 透過測試優先開發來建立全端電影投票應用程式](https://teropa.info/blog/2015/09/10/full-stack-redux-tutorial.html) - [使用 React 和 Node 建立 Twitter Stream](https://scotch.io/tutorials/build-a-real-time-twitter-stream-with-node-and-react-js) - 使用 Webtask.io 建立無伺服器 MERN Story 應用程式 ``` - [Part 1](https://scotch.io/tutorials/build-a-serverless-mern-story-app-with-webtask-io-zero-to-deploy-1) ``` ``` - [Part 2](https://scotch.io/tutorials/build-a-serverless-mern-story-app-with-webtask-io-zero-to-deploy-2) ``` - [使用 React + Parcel 建立 Chrome 擴充功能](https://medium.freecodecamp.org/building-chrome-extensions-in-react-parcel-79d0240dd58f) ``` [Testing React App With Pupepeteer and Jest](https://blog.bitsrc.io/testing-your-react-app-with-puppeteer-and-jest-c72b3dfcde59) ``` - [用 React 編寫生命遊戲](https://medium.freecodecamp.org/create-gameoflife-with-react-in-one-hour-8e686a410174) - [建立帶有情感分析的聊天應用程式](https://codeburst.io/build-a-chat-app-with-sentiment-analysis-using-next-js-c43ebf3ea643) - [建立全端 Web 應用程式設置](https://hackernoon.com/full-stack-web-application-using-react-node-js-express-and-webpack-97dbd5b9d708) - 建立隨機報價機 ``` - [Part 1](https://www.youtube.com/watch?v=3QngsWA9IEE) ``` ``` - [Part 2](https://www.youtube.com/watch?v=XnoTmO06OYo) ``` ``` - [Part 3](https://www.youtube.com/watch?v=us51Jne67_I) ``` ``` - [Part 4](https://www.youtube.com/watch?v=iZx7hqHb5MU) ``` ``` - [Part 5](https://www.youtube.com/watch?v=lpba9vBqXl0) ``` ``` - [Part 6](https://www.youtube.com/watch?v=Jvp8j6zrFHE) ``` ``` - [Part 7](https://www.youtube.com/watch?v=M_hFfrN8_PQ) ``` - 使用 Angular 6 建立美麗的現實世界應用程式: ``` - [Part I](https://medium.com/@hamedbaatour/build-a-real-world-beautiful-web-app-with-angular-6-a-to-z-ultimate-guide-2018-part-i-e121dd1d55e) ``` - [使用 BootStrap 4 和 Angular 6 建立響應式佈局](https://medium.com/@tomastrajan/how-to-build-responsive-layouts-with-bootstrap-4-and-angular-6-cfbb108d797b) - [使用 Django 和測試驅動開發建立待辦事項列表](http://www.obeythetestinggoat.com/) - [使用 Python 建立 RESTful 微服務](http://www.skybert.net/python/developing-a-restful-micro-service-in-python/) - [使用 Docker、Flask 和 React 的微服務](https://testdriven.io/) - [使用 Flask 建立簡單的 Web 應用程式](https://pythonspot.com/flask-web-app-with-python/) - [使用 Flask 建立 RESTful API – TDD 方式](https://scotch.io/tutorials/build-a-restful-api-with-flask-the-tdd-way) - [在 20 分鐘內建立 Django API](https://codeburst.io/create-a-django-api-in-under-20-minutes-2a082a60f6f3) 想法 == 簡單的 --- ### 99 瓶 - 建立一個程序,列印歌曲“牆上的 99 瓶啤酒”的每一行。 - 不要使用所有數字的列表,也不要手動輸入所有數字。請改用內建函數。 - 除了短語“取下一個”之外,您不得直接在歌詞中輸入任何數字/數字名稱。 - 請記住,當您還剩下 1 瓶時,「瓶子」一詞將變為單數。 ### 魔術8球 - 模擬神奇的 8 球。 - 允許使用者輸入他們的問題。 - 顯示正在進行的訊息(即“思考”)。 - 建立 20 個回應,並顯示隨機回應。 - 允許用戶提出另一個問題或退出。 - 獎金: ``` - Add a gui. ``` ``` - It must have a box for users to enter the question. ``` ``` - It must have at least 4 buttons: ``` ``` - ask ``` ``` - clear (the text box) ``` ``` - play again ``` ``` - quit (this must close the window) ``` ### 石頭剪刀布遊戲 - 建立一個石頭剪刀布遊戲。 - 讓玩家選擇石頭、剪刀或布。 - 讓計算機選擇它的移動方式。 - 比較選擇並決定誰獲勝。 - 列印結果。 - 子目標: ``` - Give the player the option to play again. ``` ``` - Keep a record of the score (e.g. Player: 3 / Computer: 6). ``` ### 倒數時鐘 - 建立一個程序,允許使用者選擇時間和日期,然後以給定的時間間隔(例如每秒)列印一條訊息,告訴使用者距離所選時間還有多長時間。 - 子目標: ``` - If the selected time has already passed, have the program tell the user to start over. ``` ``` - If your program asks for the year, month, day, hour, etc. separately, allow the user to be able to type in either the month name or its number. ``` ``` - TIP: Making use of built in modules such as time and datetime can change this project from a nightmare into a much simpler task. ``` 中等的 --- ### 番茄計時器 建立一個番茄計時器。 番茄計時器是一種時間管理方法。該技術使用計時器將工作分解為多個時間間隔,通常長度為 25 分鐘,中間間隔短暫的休息。這些間隔被命名為“pomodoros”,是意大利語單字“pomodoro”(番茄)的英文複數形式,以西里洛在大學時使用的番茄形狀的廚房計時器命名。 原始技巧有六個步驟: 決定要完成的任務。 設定番茄計時器(傳統上為 25 分鐘)。 完成任務。 當計時器響起時結束工作並在一張紙上畫上複選標記。 如果您的複選標記少於四個,請短暫休息(3-5 分鐘),然後轉到步驟 2。 四個番茄鐘後,休息較長時間(15-30 分鐘),將複選標記計數重設為零,然後轉到步驟 1。 要了解有關番茄計時器的更多訊息[,請單擊此處](https://en.wikipedia.org/wiki/Pomodoro_Technique) ### 谷歌案例 - 這是一個可以讓你玩英文句子的遊戲。 - 使用者將以任何格式輸入一個句子。(大寫或小寫或兩者的混合) - 程式必須將給定的句子轉換為Google大小寫。什麼是Google大小寫句子風格?\[know\_about\_it\_here:\](這是一種寫作風格,我們將所有小寫字母替換為大寫字母,留下所有單字的首字母)。 - 子目標: ``` - Program must then convert the given sentence in camel case.To know more about camel case ``` ``` [click_here](https://en.wikipedia.org/wiki/Camel_case) ``` ``` - Sentence can be entered with any number of spaces. ``` ### 擲骰子模擬器 - 允許使用者輸入骰子的面數以及應擲骰子的次數。 - 您的程式應該模擬擲骰子並追蹤每個數字出現的次數(這不必顯示)。 - 最後,列印出每個數字出現的次數。 - 子目標: ``` - Adjust your program so that if the user does not type in a number when they need to, the program will keep prompting them to type in a real number until they do so. ``` ``` - Put the program into a loop so that the user can continue to simulate dice rolls without having to restart the entire program. ``` ``` - In addition to printing out how many times each side appeared, also print out the percentage it appeared. If you can, round the percentage to 4 digits total OR two decimal places. ``` - 獎金: ``` - You are about to play a board game, but you realize you don't have any dice. Fortunately you have this program. ``` ``` - 1. Create a program that opens a new window and draws 2 six-sided dice ``` ``` - 2. Allow the user to quit, or roll again ``` ``` - Allow the user to select the number of dice to be drawn on screen(1-4) 2. Add up the total of the dice and display it ``` ### 計算並修復綠雞蛋和火腿 你們有些人可能還記得蘇博士的故事「綠雞蛋和火腿」。對於那些不記得或從未聽說過的人,[這](http://pastebin.com/XMY48CnN)是這個故事。然而,我給你的故事有一個問題——每次使用「我」這個詞時,它都是小寫的。 由於此問題,您的工作是執行以下操作: - 將我給您的故事複製到常規文字檔案中。 - 建立一個程式來通讀故事並在任何時候將字母 i 變為大寫。 (當它也用在 sam-I-am 的名字中時,請務必更改它。) - 讓你的程式建立一個新文件,並讓它正確地寫出故事。 - 印出有多少錯誤被修正。 - 完成後,您應該已經糾正了[這麼多](https://i.imgur.com/GRkj3yz.jpg)錯誤。 難的 -- ### 隨機維基百科文章 如果您曾造訪維基百科,您可能已經注意到螢幕左側有一個指向隨機文章的連結。雖然看到您被帶到哪篇文章可能很有趣,但有時看到文章的名稱會很好,這樣您就可以在聽起來很無聊時跳過它。幸運的是,維基百科有一個 API,允許我們這樣做[點擊這裡](https://en.wikipedia.org/w/api.php?action=query&list=random&rnnamespace=0&rnlimit=10&format=json)。 然而,有一個困境。由於維基百科擁有有關世界各地主題的文章,其中一些文章的標題中包含特殊字元。例如,關於西班牙畫家[埃拉斯托·科爾特斯·華雷斯 (Erasto Cortés Juárez)](https://en.wikipedia.org/wiki/Erasto_Cort%C3%A9s_Ju%C3%A1rez)的文章中就有 é 和 á。如果您查看這篇特定文章的[API](https://en.wikipedia.org/w/api.php?action=query&prop=info&pageids=39608394&inprop=url&format=json) ,您將看到標題是“Erasto Cort\\u00e9s Ju\\u00e1rez”,並且 \\u00e9 和 \\u00e1 正在替換前面提到的兩個字母。 (有關這是什麼的訊息,請首先查看文件中[本頁](https://docs.python.org/2/howto/unicode.html)的前半部分)。為了讓你的程式正常運作,你必須以某種方式處理這個問題。 - 建立一個程序,從官方維基百科 API 中提取標題,然後一一詢問用戶是否願意閱讀該文章。 - 例子: ``` - If the first title is Reddit, then the program should ask something along the lines of "Would you like to read about Reddit?" If the user says yes, then the program should open up the article for the user to read. ``` ``` - HINT: Click [here](https://en.wikipedia.org/wiki?curid=39608394) to see how the article's ID can be used to access the actual article. ``` - 子目標: ``` - As mentioned before, do something about the possibility of unicode appearing in the title. ``` ``` - Whether you want your program to simply filter out these articles or you want to actually turn the codes into readable characters, that's up to you. ``` ``` - Make the program pause once the user has selected an article to read, and allow him or her to continue browsing different article titles once finished reading. ``` ``` - Allow the user to simply press ENTER to be asked about a new article. ``` ### 天氣如何? 如果您想了解 API 的基礎知識,請查看 iamapizza 的[這篇](http://www.reddit.com/r/explainlikeimfive/comments/qowts/eli5_what_is_api/c3z9kok)文章。 - 建立一個程序,從 OpenWeatherMap.org 提取資料並列印有關當前天氣的訊息,例如您居住的地方的最高氣溫、最低氣溫和雨量。 - 子目標: ``` - Print out data for the next 5-7 days so you have a 5 day/week long forecast. ``` ``` - Print the data to another file that you can open up and view at, instead of viewing the information in the command line. ``` ``` - If you know html, write a file that you can print information to so that your project is more interesting. ``` - 尖端: ``` - APIs that are in Json are essentially lists and dictionaries. Remember that to reference something in a list, you must refer to it by what number element it is in the list, and to reference a key in a dictionary, you must refer to it by its name. ``` ``` - Don't like Celsius? Add &units=imperial to the end of the URL of the API to receive your data in Fahrenheit. ``` ### 來源 - https://github.com/tuvtran/project-based-learning - https://github.com/jorgegonzalez/beginner-projects - https://github.com/MunGell/awesome-for-beginners/blob/master/README.md - https://github.com/sarahbohr/AbsoluteBeginnerProjects --- 你怎麼認為?您喜歡透過特定專案進行學習還是不喜歡透過特定專案進行學習? --- 原文出處:https://dev.to/samborick/100-project-ideas-oda

學習 Rust:一個乾淨的開始

我決定是時候學習[Rust 了](https://www.rust-lang.org/),為了保持自己的動力,我將在這裡記錄學習的進展。 ![費里斯螃蟹](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/t0xl5mafhbjgfuowu62t.png) 有關於我的一些;我是一名 Web 開發人員,雖然已經涉足多年,但已經從事了大約 5 年。我有使用[Perl](https://www.perl.org/)和[PHP](https://www.php.net/)的經驗,但我的日常工作是 JavaScript/TypeScript,無論是透過[NodeJS](https://nodejs.org/en)還是[ReactJS](https://react.dev/) 。我想學習 Rust 沒有什麼特別的原因,只是學習新事物很有趣。 我的第一個停靠點是Google `learn rust` ,這引導我找到了[「這本書」](https://doc.rust-lang.org/book/) 。這本書是 Rust 社群為新手(或所謂的 Rustlings)編寫的入門指南,旨在「紮實掌握這門語言」。 公共學習 ---- 我選擇公開記錄我的 Rust 學習之旅,因為我相信公開學習的力量。透過分享我的成功、挑戰和見解,我將加強自己的理解,並希望為其他走類似道路的人提供資源。 我親眼目睹了這種方法的價值。我邀請讀者提供回饋、更正和貢獻。雖然我認識到公共學習並不適合所有人,但我個人發現它非常有益,並希望激勵其他人考慮它。那麼,讓我們深入學習這些課程。 第 1 課“入門” --------- 本課分為 3 個部分: - 安裝 - 你好世界! - 你好,貨物! ### 安裝 看到列出的安裝,我鬆了口氣,我擔心我必須查找如何安裝 Rust。我使用的是 Windows 計算機,但決定在 Linux 中學習 Rust,因此我將透過 WSL 使用 Ubuntu。 安裝指令看起來很簡單,它使用curl來下載一些東西,然後透過sh進行管道傳輸,所以我們可以假設下載的專案是某種bash腳本。 ``` curl --proto '=https' --tlsv1.2 https://sh.rustup.rs -sSf | sh ``` 不管你信不信,這是我犯下的第一個錯誤。我看到`Rust is installed now. Great!`訊息並繼續下一課。如果我繼續閱讀下去,我會發現我需要單獨安裝編譯器。 > Linux 使用者通常應該根據其發行版的文件安裝 GCC 或 Clang。例如,如果您使用 Ubuntu,則可以安裝 build-essential 套件。 不過,這很容易解決,我很快就回到了正軌。 ``` sudo apt install build-essential ``` ### 你好世界! 下一部分是開發社群的主要內容,即深受喜愛的“Hello, World!”例子。 ![你好世界](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/l2navm68azq2jbk9mcsf.png) 我在這裡學到了一些東西,函數是用`fn`關鍵字聲明的,任何 Rust 應用程式的入口點都是`main.rs`檔案中的`main`函數,標準命名約定是使用下劃線來分隔函數和檔案名稱中的單字。 正是在這個階段,我發現我沒有安裝編譯器,我認為這是像這樣的簡單部分的真正原因,以確保我們都設定正確。 ### 你好,貨物! 上一節很簡單,這節也很簡單,但向我們介紹了[Cargo](https://crates.io/) ,它是 Rust 的套件管理器,作為一個 JS 開發者,我的腦海裡直接想到了 NPM。 Cargo 允許我們做一些很酷的事情: - 為我們的包命名。 - 新增包依賴項。 - 用一個命令執行我們的程式。 - 使用除錯模式和發布模式來建立我們的程式。 - 檢查我們的程式是否編譯,但沒有實際建立它。 這個範例讓我們重新創造我們的`Hello, World!`例如但以貨運方式。程式碼非常簡單,幾乎不值得展示,但它就是這樣。 ``` fn main() { println!("Hello, world!"); } ``` 第 2 課“猜謎遊戲” ----------- 第二課沒有任何小節,本課的目標是編寫一個猜謎遊戲,用戶輸入一個數字,我們將其與隨機選擇的數字進行比較,遊戲繼續,直到用戶猜出確切的數字。 我們仍然沒有做任何突破性的事情,但從列印靜態文字到動態獲取用戶輸入並返回結果的進展仍然很好。 ### VS程式碼 正是在這一點上,我決定在`nano`中進行程式碼變更不是一個好主意,我需要在 VSCode 中開啟專案。我加入了一些擴展,希望能讓開發變得更容易。這些是[rust-analyzer](https://marketplace.visualstudio.com/items?itemName=rust-lang.rust-analyzer) 、[板條箱](https://marketplace.visualstudio.com/items?itemName=serayuzgur.crates)和[Even Better TOML](https://marketplace.visualstudio.com/items?itemName=tamasfe.even-better-toml) 。你可以使用任何你喜歡的編輯器,我只是習慣了 VSCode。 ![VSCode 標誌](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rq9m8kkxv6milsxbv5zw.png) ### 製作遊戲 讓我們來看看遊戲教程,它讓我們使用貨物來設定專案,並很快向我們介紹了一些新概念 - `use`關鍵字。 - 可變變數。 - 錯誤處理。 - 文件位置 #### `use`關鍵字 `use`關鍵字允許我們從其他庫中提取程式碼,作為一名 Web 開發人員,我想將其與[import](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import)進行比較。預設情況下,Rust 將能夠存取「標準」庫中的一組專案,這稱為前奏,但如果您想存取其他任何內容,則必須使用`use` 。 在他們給出的範例中,我們確實`use std::io;`它允許我們存取`io`命名空間,這確實感覺有點奇怪,因為我們已經可以存取`std` ,這意味著`std::io`也可以存取。 #### 可變變數 在 JavaScript 領域,我們有不可變變數和可變變數的概念,它們是`const`和`let` ,其中`const`是不可變的,而`let`不是。 Rust 有點不同,因為除非另有說明,否則所有變數都是不可變的,變數關鍵字也總是`let` ,或者至少據我所知到目前為止是這樣。 ``` let mut var1 = String::new(); // mutable let mut var2 = String::from("Test String"); // mutable let var3 = 6; // immutable ``` 這本書讓我們知道,第三課將回歸可變性。 #### 錯誤處理 我們介紹了兩種類型的錯誤處理`.expect` ,它們不會嘗試任何類型的恢復,但會在應用程式崩潰和`match`時發布一條訊息。 `Match`從函數中取得`Result` ,然後允許您根據`Result`呼叫函數。在範例中,我們給出了`parse`並告訴它要么是`Ok`要么是`Err` ,在`match`中我們可以定義一個在這兩種情況下呼叫的函數。我假設當我們開始處理更多樣化的函數時,match 將能夠處理所有`Result`類型。 #### 文件位置 這是迄今為止我最喜歡 Rust 的部分,我知道它不應該那麼令人興奮,但我認為它是。當您執行命令`cargo doc` Cargo 時,Cargo 將掃描您正在使用的所有程式碼,並產生解釋功能以及如何使用它們的說明頁面。 目前還沒有太多解釋,但我希望這些文件是從程式碼中的註解產生的,即使這不是那種情況,可以自我記錄的程式碼庫對我來說是如此有趣。 ### 偏離了人跡罕至的地方 此時,我已經完成了前兩課,並決定對猜謎遊戲進行一些更改。我將遊戲循環提取到它自己的函數中,並加入了解析失敗的錯誤訊息。 我不喜歡的一件事是這條線的`magic` 。 ``` let guess: u32 = match guess.trim().parse() ``` 我不喜歡這種感覺,就像 parse 神奇地知道它的目標類型一樣。所以我閱讀了 VSCode 中的解析工具提示,它教導了有關`turbofish`語法的內容。我不知道人們是否不喜歡這種語法,或者這本書的作者是否認為它對於初學者來說太複雜,但在我看來,它更有意義。我們告訴 parse 我們想要什麼類型,然後我們的`let`從中推論出類型,而不是相反。 ``` let guess = match guess.trim().parse::<u32>() ``` 這是修改後的程式碼。 {% 嵌入 https://replit.com/@andrewb05/Guessing-game %} 註銷 -- 感謝您與我一起踏上這段旅程。我計劃繼續這個系列並涵蓋整本書。如果您想關注,可以按下「關注」按鈕以獲得新帖子的通知。 正如我之前所說,請隨意留下任何反饋,如果您也在公開學習,請在評論中留下您的系列的連結,以便我可以查看。 非常感謝您的閱讀。如果您想在開發之外與我聯繫,這裡有我的[Twitter](https://twitter.com/Link2Twenty)和[linkedin,](https://www.linkedin.com/in/andrew-bone-ba241b179/)歡迎來打個招呼 😊。 --- 原文出處:https://dev.to/link2twenty/learning-rust-a-clean-start-4eom

2024 年每個雲端工程師都應該了解的 7 種程式語言!

近年來,在各種程式設計訓練營的指導中,我獲得了獨特的機會來指導和支援眾多熱衷於在雲端工程和 DevOps 領域取得成功的初級開發人員。我注意到這些有抱負的工程師中反覆出現的一個主題是,他們渴望深入了解雲端運算的複雜性,但常常對大量可用的程式語言和工具感到不知所措。這種認識激發了我的想法,即建立一個全面且平易近人的指南,為任何開始雲端工程之旅的人介紹基本的程式語言。 同樣,到 2024 年,每個雲端工程師都應該了解以下七種程式語言,每種語言都因其相關性、功能和在實現現代雲端解決方案中的作用而被選擇。 1. 翼 ---- ![只是一個翅膀](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/6syu6oqhs93z0sq77cvf.png) [Wing](https://github.com/winglang/wing)的設計理念強調生產力、安全性和效率,使開發人員能夠在整個開發過程中保持單一、直覺的工作流程。 透過將基礎設施資源視為一等公民,Wing 允許開發人員直接在其應用程式程式碼中定義、互動和管理這些資源。這種整合顯著降低了與管理雲端基礎架構相關的複雜性和潛在錯誤,從而更輕鬆地建置和部署安全、可擴展的應用程式。 Wing 的主要功能之一是它能夠編譯為基礎設施即程式碼 (IaC) 格式,例如 Terraform 和 JavaScript。 Wing 對雲端應用程式本地模擬的支援徹底改變了開發人員的工作效率。在部署之前能夠在本地環境中執行、視覺化、互動和除錯雲端應用程式可以顯著加快開發週期並提高應用程式品質。此功能與易於與 DevOps 實踐整合的語言設計相結合,可確保開發人員能夠更有效地應用持續整合和持續部署 (CI/CD) 方法,從而與現代軟體開發實踐保持一致。 看看[Wing 的互動遊樂場,](https://www.winglang.io/play/)了解 Wing 語言的工作原理。 使用 Wing 非常輕鬆且超級簡單。 您可以在幾秒鐘內安裝 Wing 並開始自動化您的雲端工作流程。 ``` npm install -g winglang ``` 您可以使用以下命令驗證您的安裝。 ``` wing -V ``` 使用 CLI 引導新專案:使用 new 命令,然後修改 main.w 使其具有以下內容: ``` wing new empty ``` ``` bring cloud; // define a queue, a bucket and a counter let bucket = new cloud.Bucket(); let counter = new cloud.Counter(initial: 1); let queue = new cloud.Queue(); // When a message is received in the queue it should be consumed // by the following closure queue.setConsumer(inflight (message: str) => { // Increment the distributed counter, the index variable will // store the value prior to the increment let index = counter.inc(); // Once two messages are pushed to the queue, e.g. "Wing" and "Queue". // Two files will be created: // - wing-1.txt with "Hello Wing" // - wing-2.txt with "Hello Queue" bucket.put("wing-{index}.txt", "Hello, welcome to winglang world!"); log("file wing-{index}.txt created"); }); ``` 使用 wing it 指令透過我們新建立的應用程式啟動控制台: ``` wing it main.w ``` Wing 控制台為您提供雲端應用程式的視圖,使開發人員能夠更快地迭代和熱重載: ![溫朗前衛](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mmrz484dh0fvf220uhg4.png) 透過 Wing 的有關[Wing 入門](https://www.winglang.io/docs/start-here/local)的文件探索更多資訊。 2.Python -------- ![僅限蟒蛇](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/r7gdgxhcb4mjywdih30u.png) 由於其簡單性、多功能性和強大的生態系統, [Python](https://github.com/python)仍然是雲端工程師不可或缺的語言。其廣泛的庫和框架集合(例如用於 Web 應用程式的 Flask 和用於機器學習的 TensorFlow)使 Python 成為開發各種基於雲端的服務的首選語言。此外,Python 在自動化、腳本編寫和資料分析中的作用確保了它仍然是雲端基礎設施管理、自動化任務和雲端應用程式快速原型設計的關鍵工具。 3. 成長 ----- ![戈蘭](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/p5ggz0p6ix46uqifhmd7.png) [Go](https://github.com/golang/go)或 Golang 由 Google 設計,在雲端工程師中越來越受歡迎,用於建立高效能和可擴展的雲端服務。它的高效、簡單和內建的並發支援使其成為開發微服務、分散式系統和容器化應用程式的絕佳選擇。 Go 與雲端平台的兼容性及其有效處理繁重網路流量和複雜處理任務的能力有助於其在雲端基礎設施專案中的日益普及。 4. JavaScript(使用 Node.js) ------------------------- ![Node.js 語言](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/s5q16t3w3zf8xctgrlvg.png) [JavaScript](https://en.wikipedia.org/wiki/JavaScript) ,特別是與 Node.js 一起使用時,對於專注於建置和部署可擴展且高效的 Web 應用程式的雲端工程師來說至關重要。 Node.js 允許在伺服器端使用 JavaScript,從而能夠開發適合雲端的快速、非阻塞、事件驅動的應用程式。 JavaScript 在客戶端和伺服器端開發中的普遍存在也促進了全端開發能力,使其對於從事基於雲端的 Web 服務和應用程式的工程師來說非常寶貴。 5. 生鏽 ----- ![長時間休息](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/c3f1w421ksertrrldyod.png) [Rust](https://www.rust-lang.org/)由於強調安全性、速度和無需垃圾收集器的並發性而在雲端運算領域獲得了發展勢頭。這些功能使 Rust 成為尋求開發高效能、安全且可靠的雲端服務和基礎設施的雲端工程師的有吸引力的選擇。 Rust 的記憶體安全保證和機器程式碼的高效編譯使其成為雲端環境中系統級和嵌入式應用程式的理想語言,在雲端環境中,效能和安全性至關重要。 6. Kubernetes YAML ------------------ ![Kubernetes yaml](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mga2ylbbc9g98w4hjkmg.png) 雖然[Kubernetes YAML](https://kubernetes.io/docs/concepts/overview/working-with-objects/) (YAML 不是標記語言)不是傳統意義上的程式語言,但對於使用 Kubernetes(容器編排事實上的標準)的雲端工程師來說至關重要。掌握 Kubernetes YAML 對於跨雲端環境定義、部署和管理容器化應用程式至關重要。了解 Kubernetes 資源檔案和配置的複雜性使工程師能夠利用容器編排的全部功能,確保可擴展、有彈性且高效的雲端原生應用程式。 7.Terraform HCL(HashiCorp配置語言) ------------------------------ ![地形鹽酸鹽](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ke9hjhkw6k2i9zald105.png) [Terraform HCL](https://github.com/hashicorp/hcl) (HashiCorp 配置語言)是 2024 年雲端工程師的必備語言,尤其是那些參與基礎設施即程式碼 (IaC) 實踐的工程師。 HCL 是 Terraform 使用的配置語言,Terraform 是一種廣泛採用的工具,使工程師能夠使用聲明性配置方法定義、配置和管理雲端基礎架構。學習 Terraform HCL 使雲端工程師能夠自動化跨不同服務供應商的雲端資源部署和生命週期管理,確保雲端環境的一致性、可重複性和可擴展性。 ### 包起來 到 2024 年,所有語言都有自己的優勢,我很高興將自己關於雲端工程和 DevOps 的想法放在一起。 如果我能為我的學生提供建議,在這個不斷發展的領域迅速擴展的過程中,掌握 Wing 將成為一個令人信服的選擇。 [Wing](https://www.winglang.io/)為雲端工程師和開發人員提供了獨特的優勢,提供控制臺本地測試、熱重載(對大多數雲端工程師來說是一個挑戰)和增強的可擴展性,更不用說雲端應用程式的安全性了。 --- 原文出處:https://dev.to/pavanbelagatti/7-programming-languages-every-cloud-engineer-should-know-in-2024-1kcd

使用外掛程式和主題在 OhMyZsh 和 Hyper 上設定自動完成功能的初學者指南!

您的普通 bash 可能具有您通常需要的功能,但**如果您是常規終端用戶,zsh 將改變您鍵入命令的方式。** zsh、ohmyzsh 和 hyper 一起提供的功能將讓您大吃一驚。 > 您知道您可以從終端控制 Spotify 嗎?是的,超級插件可以讓您做到這一點。 對於初學者來說,設定這些東西可能會讓人不知所措,所以這裡有一個非常簡單的入門指南! 🤩 --- 🔥 簡介 ---- 如果您使用的是如下所示的常規終端,則您會錯過 OhMyZsh 提供的許多功能。 ![Flaviocope 的 MacOS 終端](https://flaviocopes.com/macos-terminal-setup/Screenshot%202019-01-29%20at%2018.34.04.png) 今天,您將進行終端改造,使其看起來像這樣... ![我的超級終端](https://i.ibb.co/DW05RzF/Hyper-Terminal-Kumar-Abhirup.jpg) 不僅僅是外觀,OhMyZsh 還具有豐富的功能來點亮您的程式設計之旅。 在教程結束時,這就是您可以在終端機中執行的操作... - NPM、Git 自動完成 - 在終端機中輸入時自動建議 - 語法高亮顯示指令是否已定義 - 使用遊標編輯終端命令 - 查看目前目錄的`git branch`和`git status` - 開啟與目前分頁相同目錄的新分頁 - 使用 OhMyZsh 功能,例如不使用`cd`進行導航、使用`ll` 、更簡單的基於 Tab 鍵單擊的導航等等! --- ❤️ 開始吧 ------ 首先,您必須安裝`zsh` 。在某些情況下(取決於您正在執行的作業系統),它可能已經安裝。因此,請透過在終端機中執行`zsh --version`檢查它是否已安裝。 `zsh`在不同作業系統的安裝過程有所不同。查看[Zsh 安裝指南](https://github.com/robbyrussell/oh-my-zsh/wiki/Installing-ZSH)來安裝 zsh。 安裝 Zsh 後,請確保將其設為預設 shell。為此,請在終端機中執行以下命令。 ``` $ sudo chsh -s $(which zsh) ``` 登出並登入回預設 shell。執行`echo $SHELL`並預期輸出`/bin/zsh`或類似內容。 --- 🔰 安裝 OhMyZsh ------------ > 請注意,zsh 和 OhMyZsh 是不同的。 透過在終端機中執行以下命令來安裝`OhMyZsh` 。 ``` $ sudo sh -c "$(curl -fsSL https://raw.githubusercontent.com/robbyrussell/oh-my-zsh/master/tools/install.sh)" ``` 當您安裝 OhMyZsh 時,它會附帶許多插件來幫助您! 若要新增實用的插件,請在 TextEdit/Notepad/Vim/VSCode 中開啟`~/.zshrc` 。 在檔案中看到的插件清單中,只需新增一個名為`npm`的插件,如下所示 👇 ``` plugins=( git bundler dotenv osx rake rbenv ruby npm # you added this ) ``` 瞧!您已經完成了 OhMyZsh!若要查看更改,請在終端機中執行`source ~/.zshrc` ,現在您就擁有了 OhMyZsh shell 的功能。 --- 🔰 依時間安裝 HyperTerm ----------------- Zeit(now.sh 和 Next.js 的建立者)為我們建立了一個很棒的終端應用程式,它是用 Electron 建置的。 從[這裡](https://hyper.is/)下載 Hyper。 --- ### ⚛️ 使用 OhMyZsh 設定 Hyper 打開超級終端機。您不會看到 OhMyZsh 在那裡執行。因此,請轉到超級設定。在 OSX 上,它是`Hyper > Preferences` 。 這將在您最喜歡的編輯器中開啟一個`.hyper.js`檔案。該文件包含您的終端的所有設置,非常容易控制! 若要在 Hyper 中啟用 OhMyZsh 作為預設 shell,請在`.hyper.js`中進行此變更 👇 ``` - shell: '/bin/bash' + shell: '/bin/zsh' ``` **這將使 OhMyZsh 成為您的預設超級終端 shell!** --- ### 🤩 輸入指令時自動完成 Git 將`zsh-autocomplete`插件複製到 OhMyZsh 插件資料夾中。 ``` $ sudo git clone https://github.com/zsh-users/zsh-autosuggestions ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-autosuggestions ``` 完成後,將外掛程式新增至`~/.zshrc`檔案的外掛程式清單中。 ``` plugins=( ... zsh-autosuggestions ) ``` --- ### 🎉 Zsh 語法高亮 Git 將`zsh-syntax-highlighting`外掛程式克隆到 OhMyZsh 外掛程式資料夾中。 ``` $ sudo git clone https://github.com/zsh-users/zsh-syntax-highlighting.git ${ZSH_CUSTOM:-~/.oh-my-zsh/custom}/plugins/zsh-syntax-highlighting ``` 並再次將其新增至`.zshrc`檔案的外掛程式清單。 ``` plugins=( ... zsh-syntax-highlighting ) ``` > 注意:若要反映您所做的每項更改,請在終端機中執行`source ~/.zshrc` 。 --- ### 📯 啟用 Hyper 相關功能與主題 透過切換超級終端的設定來開啟`.hyper.js` 。 請查看`plugins: [...]`部分並將這些插件名稱貼到此處。 ``` plugins: [ ... 'hypercwd', 'hyper-statusline', 'hyper-alt-click', 'hyperterm-safepaste', 'hyper-search', 'hypergoogle', 'hyperborder', 'hyper-tab-icons', 'hyper-hide-title', 'shades-of-purple-hyper' ], ``` 儲存文件,Hyper 會自動為您安裝這些外掛程式和主題。要反映更改,只需關閉並再次啟動超級終端即可。 萬歲!**現在,您的終端機中已擁有本 DEV.to 文章開頭列出的所有功能。** --- 獎勵:在 VSCode 中為整合終端設定相同的終端配置 --------------------------- 在 VSCode 設定中,新增以下 JSON 鍵值對,然後就可以開始了! ``` { ... "terminal.integrated.shell.osx": "/bin/zsh", "terminal.integrated.fontSize": 16 } ``` **就是這樣,夥計們!** --- 🔥 資源 ---- - <https://ohmyz.sh> - <https://hyper.is> --- 🏆 關於我 ----- **我是 Kumar Abhirup,一位來自印度的 16 歲 JavaScript React 開發人員,每天都在學習新事物。** [在 Twitter 上與我聯絡 🐦](https://twitter.com/kumar_abhirup) [我的個人網站和作品集🖥️](https://kumar.now.sh) *請在下面評論您更好的方法以及改進本文的建議。 :)* --- 原文出處:https://dev.to/kumareth/a-beginner-s-guide-for-setting-up-autocomplete-on-ohmyzsh-hyper-with-plugins-themes-47f2

我正在建立一個全端應用程式:以下是我將要使用的庫......

您可以使用無數的框架和函式庫來改進您的全端應用程式。 我們將介紹令人興奮的概念,例如應用程式內通知、使用 React 製作影片、從為開發人員提供的電子郵件 API 到在瀏覽器中建立互動式音樂。 那我們就開始吧。 (不要忘記為這些庫加註星標以表示您的支持)。 ![圖片描述](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qqoipyuoxgb83swyoo4a.gif) https://github.com/CopilotKit/CopilotKit --- 1. [CopilotKit](https://github.com/CopilotKit/CopilotKit) - 在數小時內為您的產品提供 AI Copilot。 ------------------------------------------------------------------------------------ ![副駕駛套件](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/nzuxjfog2ldam3csrl62.png) 您可以使用兩個 React 元件將關鍵 AI 功能整合到 React 應用程式中。它們還提供內建(完全可自訂)Copilot 原生 UX 元件,例如`<CopilotKit />` 、 `<CopilotPopup />` 、 `<CopilotSidebar />` 、 `<CopilotTextarea />` 。 開始使用以下 npm 指令。 ``` npm i @copilotkit/react-core @copilotkit/react-ui @copilotkit/react-textarea ``` 這是整合 CopilotTextArea 的方法。 ``` import { CopilotTextarea } from "@copilotkit/react-textarea"; import { useState } from "react"; export function SomeReactComponent() { const [text, setText] = useState(""); return ( <> <CopilotTextarea className="px-4 py-4" value={text} onValueChange={(value: string) => setText(value)} placeholder="What are your plans for your vacation?" autosuggestionsConfig={{ textareaPurpose: "Travel notes from the user's previous vacations. Likely written in a colloquial style, but adjust as needed.", chatApiConfigs: { suggestionsApiConfig: { forwardedParams: { max_tokens: 20, stop: [".", "?", "!"], }, }, }, }} /> </> ); } ``` 您可以閱讀[文件](https://docs.copilotkit.ai/getting-started/quickstart-textarea)。 基本概念是在幾分鐘內建立可用於基於 LLM 的全端應用程式的 AI 聊天機器人。 https://github.com/CopilotKit/CopilotKit --- 2. [Storybook](https://github.com/storybookjs/storybook) - UI 開發、測試和文件變得簡單。 --------------------------------------------------------------------------- ![故事書](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/78rfum1ydisn51qhb408.png) Storybook 是一個用於獨立建立 UI 元件和頁面的前端工作坊。它有助於 UI 開發、測試和文件編制。 他們在 GitHub 上有超過 57,000 次提交、81,000 多個 star 和 1300 多個版本。 這是您為專案建立簡單元件的方法。 ``` import type { Meta, StoryObj } from '@storybook/react'; import { YourComponent } from './YourComponent'; //👇 This default export determines where your story goes in the story list const meta: Meta<typeof YourComponent> = { component: YourComponent, }; export default meta; type Story = StoryObj<typeof YourComponent>; export const FirstStory: Story = { args: { //👇 The args you need here will depend on your component }, }; ``` 您可以閱讀[文件](https://storybook.js.org/docs/get-started/setup)。 如今,UI 除錯起來很痛苦,因為它們與業務邏輯、互動狀態和應用程式上下文糾纏在一起。 Storybook 提供了一個獨立的 iframe 來渲染元件,而不會受到應用程式業務邏輯和上下文的干擾。這可以幫助您將開發重點放在元件的每個變體上,甚至是難以觸及的邊緣情況。 https://github.com/storybookjs/storybook --- 3. [Appwrite](https://github.com/appwrite/appwrite) - 您的後端減少麻煩。 --------------------------------------------------------------- ![應用程式寫入](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/8x568uz21seyygw6b72z.png) ![帶有 appwrite 的 sdk 列表](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/cp7k8qnamsluto7eifpl.png) Appwrite 的開源平台可讓您將身份驗證、資料庫、函數和儲存體新增至您的產品中,並建立任何規模的任何應用程式、擁有您的資料並使用您喜歡的編碼語言和工具。 他們有很好的貢獻指南,甚至不厭其煩地詳細解釋架構。 開始使用以下 npm 指令。 ``` npm install appwrite ``` 您可以像這樣建立一個登入元件。 ``` "use client"; import { useState } from "react"; import { account, ID } from "./appwrite"; const LoginPage = () => { const [loggedInUser, setLoggedInUser] = useState(null); const [email, setEmail] = useState(""); const [password, setPassword] = useState(""); const [name, setName] = useState(""); const login = async (email, password) => { const session = await account.createEmailSession(email, password); setLoggedInUser(await account.get()); }; const register = async () => { await account.create(ID.unique(), email, password, name); login(email, password); }; const logout = async () => { await account.deleteSession("current"); setLoggedInUser(null); }; if (loggedInUser) { return ( <div> <p>Logged in as {loggedInUser.name}</p> <button type="button" onClick={logout}> Logout </button> </div> ); } return ( <div> <p>Not logged in</p> <form> <input type="email" placeholder="Email" value={email} onChange={(e) => setEmail(e.target.value)} /> <input type="password" placeholder="Password" value={password} onChange={(e) => setPassword(e.target.value)} /> <input type="text" placeholder="Name" value={name} onChange={(e) => setName(e.target.value)} /> <button type="button" onClick={() => login(email, password)}> Login </button> <button type="button" onClick={register}> Register </button> </form> </div> ); }; export default LoginPage; ``` 您可以閱讀[文件](https://appwrite.io/docs)。 Appwrite 可以非常輕鬆地建立具有開箱即用的擴充功能的可擴展後端應用程式。 https://github.com/appwrite/appwrite --- 4. [Wasp](https://github.com/wasp-lang/wasp) - 用於 React、node.js 和 prisma 的類似 Rails 的框架。 --------------------------------------------------------------------------------------- ![黃蜂](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/fi2mwazueoc3ezjx8a9q.png) 使用 React 和 Node.js 開發全端 Web 應用程式的最快方法。這不是一個想法,而是一種建立瘋狂快速全端應用程式的不同方法。 這是將其整合到元件中的方法。 ``` import getRecipes from "@wasp/queries/getRecipes"; import { useQuery } from "@wasp/queries"; import type { User } from "@wasp/entities"; export function HomePage({ user }: { user: User }) { // Due to full-stack type safety, `recipes` will be of type `Recipe[]` here. const { data: recipes, isLoading } = useQuery(getRecipes); // Calling our query here! if (isLoading) { return <div>Loading...</div>; } return ( <div> <h1>Recipes</h1> <ul> {recipes ? recipes.map((recipe) => ( <li key={recipe.id}> <div>{recipe.title}</div> <div>{recipe.description}</div> </li> )) : 'No recipes defined yet!'} </ul> </div> ); } ``` 您可以閱讀[文件](https://wasp-lang.dev/docs)。 https://github.com/wasp-lang/wasp --- 5. [Novu](https://github.com/novuhq/novu) - 將應用程式內通知新增至您的應用程式! -------------------------------------------------------------- ![再次](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/716b7biilet4auudjlcu.png) Novu 提供開源通知基礎架構和功能齊全的嵌入式通知中心。 這就是如何使用`React`建立 novu 元件以用於應用程式內通知。 ``` import { NovuProvider, PopoverNotificationCenter, NotificationBell, } from "@novu/notification-center"; function App() { return ( <> <NovuProvider subscriberId={process.env.REACT_APP_SUB_ID} applicationIdentifier={process.env.REACT_APP_APP_ID} > <PopoverNotificationCenter> {({ unseenCount }) => <NotificationBell unseenCount={unseenCount} />} </PopoverNotificationCenter> </NovuProvider> </> ); } export default App; ``` 您可以閱讀[文件](https://docs.novu.co/getting-started/introduction)。 https://github.com/novuhq/novu --- 6. [Remotion](https://github.com/remotion-dev/remotion) - 使用 React 以程式設計方式製作影片。 ------------------------------------------------------------------------------- ![遠端](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wmnrxhsc7b9mm5oagflm.png) 使用 React 建立真正的 MP4 影片,使用伺服器端渲染和參數化擴展影片製作。 開始使用以下 npm 指令。 ``` npm init video ``` 它為您提供了一個幀號和一個空白畫布,您可以在其中使用 React 渲染任何您想要的內容。 這是一個範例 React 元件,它將當前幀渲染為文字。 ``` import { AbsoluteFill, useCurrentFrame } from "remotion";   export const MyComposition = () => { const frame = useCurrentFrame();   return ( <AbsoluteFill style={{ justifyContent: "center", alignItems: "center", fontSize: 100, backgroundColor: "white", }} > The current frame is {frame}. </AbsoluteFill> ); }; ``` 您可以閱讀[文件](https://www.remotion.dev/docs/)。 過去兩年,remotion 團隊因製作 GitHub Wrapped 而聞名。 https://github.com/remotion-dev/remotion --- [7.NocoDB](https://github.com/nocodb/nocodb) - Airtable 的替代品。 ------------------------------------------------------------- ![諾科資料庫](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/iw3tchfgyzehye5c39xq.png) Airtable 的免費開源替代品是 NocoDB。它可以使用任何 MySQL、PostgreSQL、SQL Server、SQLite 或 MariaDB 資料庫製作智慧型電子表格。 其主要目標是讓強大的計算工具得到更廣泛的使用。 開始使用以下 npx 指令。 ``` npx create-nocodb-app ``` 您可以閱讀[文件](https://docs.nocodb.com/)。 NocoDB 的建立是為了為世界各地的數位企業提供強大的開源和無程式碼資料庫介面。 您可以非常快速地將airtable資料匯入NocoDB。 https://github.com/nocodb/nocodb --- 8.[新穎](https://github.com/steven-tey/novel)- 所見即所得編輯器,具有人工智慧自動完成功能。 ------------------------------------------------------------------- ![小說](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/uo34vd9twpxcpbpzgchi.png) 它使用`Next.js` 、 `Vercel AI SDK` 、 `Tiptap`作為文字編輯器。 開始使用以下 npm 指令。 ``` npm i novel ``` 您可以這樣使用它。有多種選項可用於改進您的應用程式。 ``` import { Editor } from "novel"; export default function App() { return <Editor />; } ``` https://github.com/steven-tey/novel --- 9. [Blitz](https://github.com/blitz-js/blitz) - 缺少 NextJS 的全端工具包。 ----------------------------------------------------------------- ![閃電戰](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vz6ineg1o7xyv7pwbuqn.png) Blitz 繼承了 Next.js 的不足,為全球應用程式的交付和擴展提供了經過實戰考驗的函式庫和約定。 開始使用以下 npm 指令。 ``` npm install -g blitz ``` 這就是您如何使用 Blitz 建立新頁面。 ``` const NewProjectPage: BlitzPage = () => { const router = useRouter() const [createProjectMutation] = useMutation(createProject) return ( <div> <h1>Create New Project</h1> <ProjectForm submitText="Create Project" schema={CreateProject} onSubmit={async (values) => { // This is equivalent to calling the server function directly const project = await createProjectMutation(values) // Notice the 'Routes' object Blitz provides for routing router.push(Routes.ProjectsPage({ projectId: project.id })) }} /> </div> ); }; NewProjectPage.authenticate = true NewProjectPage.getLayout = (page) => <Layout>{page}</Layout> export default NewProjectPage ``` 您可以閱讀[文件](https://blitzjs.com/docs/get-started)。 它使建築物改善了數倍。 ![閃電戰](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/cc4mb5wdksjv1ybx71co.png) https://github.com/blitz-js/blitz --- 10. [Supabase](https://github.com/supabase/supabase) - 開源 Firebase 替代品。 ----------------------------------------------------------------------- ![蘇帕貝斯](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ksfygjhrzhmsg9cnvobs.png) 我們大多數人都已經預料到 SUPABASE 會出現在這裡,因為它實在是太棒了。 開始使用以下 npm 指令 (Next.js)。 ``` npx create-next-app -e with-supabase ``` 這是使用 supabase 建立用戶的方法。 ``` import { createClient } from '@supabase/supabase-js' // Initialize const supabaseUrl = 'https://chat-room.supabase.co' const supabaseKey = 'public-anon-key' const supabase = createClient(supabaseUrl, supabaseKey) // Create a new user const { user, error } = await supabase.auth.signUp({ email: '[email protected]', password: 'example-password', }) ``` 您可以閱讀[文件](https://supabase.com/docs)。 您可以使用身份驗證、即時、邊緣功能、儲存等功能建立一個速度極快的應用程式。 Supabase 涵蓋了這一切! 他們還提供了一些入門套件,例如 AI 聊天機器人和 Stripe 訂閱。 https://github.com/supabase/supabase --- [11.Refine](https://github.com/refinedev/refine) - 企業開源重組工具。 ------------------------------------------------------------ ![精煉](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qx0kd6t2jzdtf90k5ke3.png) 建立具有無與倫比的靈活性的管理面板、儀表板和 B2B 應用程式 您可以在一分鐘內使用單一 CLI 命令進行設定。 它具有適用於 15 多個後端服務的連接器,包括 Hasura、Appwrite 等。 開始使用以下 npm 指令。 ``` npm create refine-app@latest ``` 這就是使用 Refine 新增登入資訊的簡單方法。 ``` import { useLogin } from "@refinedev/core"; const { login } = useLogin(); ``` 您可以閱讀[文件](https://refine.dev/docs/)。 https://github.com/refinedev/refine --- 12. [Zenstack](https://github.com/zenstackhq/zenstack) - 資料庫到 API 和 UI 只需幾分鐘。 ----------------------------------------------------------------------------- ![禪斯塔克](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/3b6n2ea3jeeva6uujoex.png) TypeScript 工具包,透過強大的存取控制層增強 Prisma ORM,並釋放其全端開發的全部功能。 開始使用以下 npx 指令。 ``` npx zenstack@latest init ``` 這是透過伺服器適配器建立 RESTful API 的方法。 ``` // pages/api/model/[...path].ts import { requestHandler } from '@zenstackhq/next'; import { enhance } from '@zenstackhq/runtime'; import { getSessionUser } from '@lib/auth'; import { prisma } from '@lib/db'; // Mount Prisma-style APIs: "/api/model/post/findMany", "/api/model/post/create", etc. // Can be configured to provide standard RESTful APIs (using JSON:API) instead. export default requestHandler({ getPrisma: (req, res) => enhance(prisma, { user: getSessionUser(req, res) }), }); ``` 您可以閱讀[文件](https://zenstack.dev/docs/welcome)。 https://github.com/zenstackhq/zenstack --- 13. [Buildship](https://github.com/rowyio/buildship) - 低程式碼視覺化後端建構器。 -------------------------------------------------------------------- ![建造船](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rzlrynz5xephv4t9layd.png) 對於您正在使用無程式碼應用程式建構器(FlutterFlow、Webflow、Framer、Adalo、Bubble、BravoStudio...)或前端框架(Next.js、React、Vue...)建立的應用程式,您需要一個後端來支援可擴展的 API、安全工作流程、自動化等。BuildShip 為您提供了一種完全視覺化的方式,可以在易於使用的完全託管體驗中可擴展地建立這些後端任務。 這意味著您不需要在雲端平台上爭論或部署東西、執行 DevOps 等。只需立即建置和交付 🚀 https://github.com/rowyio/buildship --- 14. [Taipy](https://github.com/Avaiga/taipy) - 將資料和人工智慧演算法整合到生產就緒的 Web 應用程式中。 ----------------------------------------------------------------------------- ![打字](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ohv3johuz92lsaux52oq.png) Taipy 是一個開源 Python 庫,用於輕鬆的端到端應用程式開發, 具有假設分析、智慧管道執行、內建調度和部署工具。 開始使用以下命令。 ``` pip install taipy ``` 這是一個典型的Python函數,也是過濾器場景中使用的唯一任務。 ``` def filter_genre(initial_dataset: pd.DataFrame, selected_genre): filtered_dataset = initial_dataset[initial_dataset['genres'].str.contains(selected_genre)] filtered_data = filtered_dataset.nlargest(7, 'Popularity %') return filtered_data ``` 您可以閱讀[文件](https://docs.taipy.io/en/latest/)。 他們還有很多可供您建立的[演示應用程式教學](https://docs.taipy.io/en/latest/knowledge_base/demos/)。 https://github.com/Avaiga/taipy --- 15. [LocalForage](https://github.com/localForage/localForage) - 改進了離線儲存。 ------------------------------------------------------------------------ ![當地飼料](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4hlrka5pybvmgmo2djel.png) LocalForage 是一個 JavaScript 函式庫,它透過使用非同步資料儲存和簡單的、類似 localStorage 的 API 來改善 Web 應用程式的離線體驗。它允許開發人員儲存多種類型的資料而不僅僅是字串。 開始使用以下 npm 指令。 ``` npm install localforage ``` 只需包含 JS 檔案並開始使用 localForage。 ``` <script src="localforage.js"></script> ``` 您可以閱讀[文件](https://localforage.github.io/localForage/#installation)。 https://github.com/localForage/localForage --- 16. [Zod](https://github.com/colinhacks/zod) - 使用靜態類型推斷的 TypeScript-first 模式驗證。 ------------------------------------------------------------------------------- ![佐德](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1s6zvmqr0lv93vsrhofs.png) Zod 的目標是透過最大限度地減少重複的類型聲明來對開發人員友好。使用 Zod,您聲明一次驗證器,Zod 將自動推斷靜態 TypeScript 類型。將更簡單的類型組合成複雜的資料結構很容易。 開始使用以下 npm 指令。 ``` npm install zod ``` 這是您在建立字串架構時自訂一些常見錯誤訊息的方法。 ``` const name = z.string({ required_error: "Name is required", invalid_type_error: "Name must be a string", }); ``` 您可以閱讀[文件](https://zod.dev/)。 它適用於 Node.js 和所有現代瀏覽器 https://github.com/colinhacks/zod --- 17.[多普勒](https://github.com/DopplerHQ)- 管理你的秘密。 ----------------------------------------------- ![多普勒](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/gycxnuiiwsvibryrytlc.png) 您可以透過在具有開發、暫存和生產環境的專案中組織機密來消除機密蔓延。 開始使用以下指令 (MacOS)。 ``` $ brew install dopplerhq/cli/doppler $ doppler --version ``` 這是安裝 Doppler CLI[的 GitHub Actions 工作流程](https://github.com/DopplerHQ/cli-action)。 您可以閱讀[文件](https://docs.doppler.com/docs/start)。 ``` name: Example action on: [push] jobs: my-job: runs-on: ubuntu-latest steps: - name: Install CLI uses: dopplerhq/cli-action@v3 - name: Do something with the CLI run: doppler secrets --only-names env: DOPPLER_TOKEN: ${{ secrets.DOPPLER_TOKEN }} ``` https://github.com/DopplerHQ --- 18. [FastAPI](https://github.com/tiangolo/fastapi) - 高效能、易於學習、快速編碼、可用於生產。 ------------------------------------------------------------------------- ![快速API](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/h2awncoia6255ycl95lk.png) FastAPI 是一個現代、快速(高效能)的 Web 框架,用於基於標準 Python 類型提示使用 Python 3.8+ 建立 API。 開始使用以下命令。 ``` $ pip install fastapi ``` 這是您開始使用 FastAPI 的方式。 ``` from typing import Union from fastapi import FastAPI app = FastAPI() @app.get("/") def read_root(): return {"Hello": "World"} @app.get("/items/{item_id}") def read_item(item_id: int, q: Union[str, None] = None): return {"item_id": item_id, "q": q} ``` 您的編輯器將自動完成屬性並了解它們的類型,這是使用 FastAPI 的最佳功能之一。 您可以閱讀[文件](https://fastapi.tiangolo.com/)。 https://github.com/tiangolo/fastapi --- 19. [Flowise](https://github.com/FlowiseAI/Flowise) - 拖放 UI 來建立您的客製化 LLM 流程。 ---------------------------------------------------------------------------- ![流動](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ct732wv07pvwx0nmavp5.png) Flowise 是一款開源 UI 視覺化工具,用於建立客製化的 LLM 編排流程和 AI 代理程式。 開始使用以下 npm 指令。 ``` npm install -g flowise npx flowise start OR npx flowise start --FLOWISE_USERNAME=user --FLOWISE_PASSWORD=1234 ``` 這就是整合 API 的方式。 ``` import requests url = "/api/v1/prediction/:id" def query(payload): response = requests.post( url, json = payload ) return response.json() output = query({ question: "hello!" )} ``` 您可以閱讀[文件](https://docs.flowiseai.com/)。 https://github.com/FlowiseAI/Flowise --- 20. [Scrapy](https://github.com/scrapy/scrapy) - Python 的快速進階網頁爬行和抓取框架.. ------------------------------------------------------------------------ ![鬥志旺盛](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/k1b2y1hzdsphw43b6v7b.png) Scrapy 是一個快速的高級網路爬行和網頁抓取框架,用於爬行網站並從頁面中提取結構化資料。它可用於多種用途,從資料探勘到監控和自動化測試。 開始使用以下命令。 ``` pip install scrapy ``` 建造並執行您的網路蜘蛛。 ``` pip install scrapy cat > myspider.py <<EOF import scrapy class BlogSpider(scrapy.Spider): name = 'blogspider' start_urls = ['https://www.zyte.com/blog/'] def parse(self, response): for title in response.css('.oxy-post-title'): yield {'title': title.css('::text').get()} for next_page in response.css('a.next'): yield response.follow(next_page, self.parse) EOF scrapy runspider myspider.py ``` 您可以閱讀[文件](https://scrapy.org/doc/)。 它擁有大約 50k+ 的星星,因此對於網頁抓取來說具有巨大的可信度。 https://github.com/scrapy/scrapy --- 21. [Tone](https://github.com/Tonejs/Tone.js) - 在瀏覽器中製作互動式音樂。 ------------------------------------------------------------- ![音調.js](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/fokxsoblaohgs4tx75g3.png) 開始使用以下 npm 指令。 ``` npm install tone ``` 這是您開始使用 Tone.js 的方法 ``` // To import Tone.js: import * as Tone from 'tone' //create a synth and connect it to the main output (your speakers) const synth = new Tone.Synth().toDestination(); //play a middle 'C' for the duration of an 8th note synth.triggerAttackRelease("C4", "8n"); ``` 您可以閱讀[文件](https://github.com/Tonejs/Tone.js?tab=readme-ov-file#installation)。 https://github.com/Tonejs/Tone.js --- 22. [Spacetime](https://github.com/spencermountain/spacetime) - 輕量級 javascript 時區庫。 ----------------------------------------------------------------------------------- ![時空](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/abfyfuzt4nw4h7b8usab.png) 您可以計算遠端時區的時間;支持夏令時、閏年和半球。按季度、季節、月份、週來定位時間.. 開始使用以下 npm 指令。 ``` npm install spacetime ``` 您可以這樣使用它。 ``` <script src="https://unpkg.com/spacetime"></script> <script> var d = spacetime('March 1 2012', 'America/New_York') //set the time d = d.time('4:20pm') d = d.goto('America/Los_Angeles') d.time() //'1:20pm' </script> ``` https://github.com/spencermountain/spacetime --- 23. [Mermaid](https://github.com/mermaid-js/mermaid) - 從類似 markdown 的文字產生圖表。 ---------------------------------------------------------------------------- ![美人魚](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ggubn86xv7fznxol6fw7.png) 您可以使用 Markdown with Mermaid 等文字產生流程圖或序列圖等圖表。 這就是建立圖表的方法。 ``` sequenceDiagram Alice->>John: Hello John, how are you? loop Healthcheck John->>John: Fight against hypochondria end Note right of John: Rational thoughts! John-->>Alice: Great! John->>Bob: How about you? Bob-->>John: Jolly good! ``` 它將做出如下圖。 ![圖表](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/bbuo2ey5q2x3sjwywizg.png) 您可以閱讀[VS Code](https://docs.mermaidchart.com/plugins/visual-studio-code)的[文件](https://mermaid.js.org/intro/getting-started.html)和外掛程式。 請參閱[即時編輯器](https://mermaid.live/edit#pako:eNpVkE1PwzAMhv9KlvM-2AZj62EIxJd24ADXXLzEbaKlcUkdUDX1v5MONomcnNevXz32UWoyKAvZ4mfCoPHRQRWhVuHeO42T7XZHNhTiFb0nMdRjYelbQETRUbpTwRM1uQ2erbaoDyqI_AbnZfjZVZYFVOBCy8J2DWlLwUQHKmAwKrwRo4gnF5Xid-gd2FEAL9hSyp12pMIpNcee2ArxEhH4LG-3D7TPoAPcnhL_4WVxcgHZkfedqIjMSI5ljbEGZ_LyxwFaSbZYo5JFLg3Eg5Iq9NkHiemjC1oWHBOOZWoM8PlQ_8Un45iiLErwbRY9gcH8PUrumuHKlWs5J2oKpasGPUWfZcvctMVsNrSnlWOb9lNN9ax1xkJk-7VZzVaL1RoWS1zdLuFmuTR6P9-sy8X1vDS3V_MFyL7vfwD_bJ1W)中的範例。 https://github.com/mermaid-js/mermaid --- 24.[公共 API](https://github.com/public-apis/public-apis) - 20 多個類別的 1400 多個 API。 ------------------------------------------------------------------------------- ![公共API](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/sjapk9rwlzdl6bcyqdnl.png) 我們主要使用外部 API 來建立應用程式,在這裡您可以找到所有 API 的清單。網站連結在最後。 它在 GitHub 上擁有大約 279k+ 顆星。 ![公共API](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rld5i88smezo1naawz7a.png) 從儲存庫取得網站連結非常困難。所以,我把它貼在這裡。 網址 - [Collective-api.vercel.app/](https://collective-api.vercel.app/) https://github.com/public-apis/public-apis --- 25. [Framer Motion](https://github.com/framer/motion) - 像魔法一樣的動畫。 ----------------------------------------------------------------- ![成幀器運動](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/hn4ecqkrhs8f4729bzps.png) 可用的最強大的動畫庫之一。 Framer 使用簡單的聲明性語法意味著您編寫的程式碼更少。更少的程式碼意味著您的程式碼庫更易於閱讀和維護。 您可以建立事件和手勢,並且使用 Framer 的社區很大,這意味著良好的支援。 開始使用以下 npm 指令。 ``` npm install framer-motion ``` 您可以這樣使用它。 ``` import { motion } from "framer-motion" <motion.div whileHover={{ scale: 1.2 }} whileTap={{ scale: 1.1 }} drag="x" dragConstraints={{ left: -100, right: 100 }} /> ``` 您可以閱讀[文件](https://www.framer.com/motion/introduction/)。 https://github.com/framer/motion --- 26.[順便說一句](https://github.com/btw-so/btw)- 在幾分鐘內建立您的個人部落格。 ---------------------------------------------------------- ![順便提一句](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/gnne3lrfpolotmxkdz2m.png) 順便說一句,您可以註冊並使用,而無需安裝任何東西。您也可以使用開源版本自行託管。 ![順便提一句](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2rli7hpoccqwpvba29b4.png) 使用順便說一句建立的[範例部落格](https://www.siddg.com/about)。 https://github.com/btw-so/btw --- 27. [Formbricks](https://github.com/formbricks/formbricks) - 開源調查平台。 -------------------------------------------------------------------- ![成型磚](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tp6ggyom33vdifd3m1vt.png) Formbricks 提供免費、開源的測量平台。透過精美的應用程式內、網站、連結和電子郵件調查收集用戶旅程中每個點的回饋。在 Formbricks 之上建置或利用預先建置的資料分析功能。 開始使用以下 npm 指令。 ``` npm install @formbricks/js ``` 這就是您開始使用 formbricks 的方法。 ``` import formbricks from "@formbricks/js"; if (typeof window !== "undefined") { formbricks.init({ environmentId: "claV2as2kKAqF28fJ8", apiHost: "https://app.formbricks.com", }); } ``` 您可以閱讀[文件](https://formbricks.com/docs/getting-started/quickstart-in-app-survey)。 https://github.com/formbricks/formbricks --- 28. [Stripe](https://github.com/stripe) - 支付基礎設施。 ------------------------------------------------- ![條紋](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/79yvcgsi4744cmryh15j.png) 數以百萬計的各種規模的公司在線上和親自使用 Stripe 來接受付款、發送付款、自動化財務流程並最終增加收入。 開始使用以下 npm 指令 (React.js)。 ``` npm install @stripe/react-stripe-js @stripe/stripe-js ``` 這就是使用鉤子的方法。 ``` import React, {useState} from 'react'; import ReactDOM from 'react-dom'; import {loadStripe} from '@stripe/stripe-js'; import { PaymentElement, Elements, useStripe, useElements, } from '@stripe/react-stripe-js'; const CheckoutForm = () => { const stripe = useStripe(); const elements = useElements(); const [errorMessage, setErrorMessage] = useState(null); const handleSubmit = async (event) => { event.preventDefault(); if (elements == null) { return; } // Trigger form validation and wallet collection const {error: submitError} = await elements.submit(); if (submitError) { // Show error to your customer setErrorMessage(submitError.message); return; } // Create the PaymentIntent and obtain clientSecret from your server endpoint const res = await fetch('/create-intent', { method: 'POST', }); const {client_secret: clientSecret} = await res.json(); const {error} = await stripe.confirmPayment({ //`Elements` instance that was used to create the Payment Element elements, clientSecret, confirmParams: { return_url: 'https://example.com/order/123/complete', }, }); if (error) { // This point will only be reached if there is an immediate error when // confirming the payment. Show error to your customer (for example, payment // details incomplete) setErrorMessage(error.message); } else { // Your customer will be redirected to your `return_url`. For some payment // methods like iDEAL, your customer will be redirected to an intermediate // site first to authorize the payment, then redirected to the `return_url`. } }; return ( <form onSubmit={handleSubmit}> <PaymentElement /> <button type="submit" disabled={!stripe || !elements}> Pay </button> {/* Show error message to your customers */} {errorMessage && <div>{errorMessage}</div>} </form> ); }; const stripePromise = loadStripe('pk_test_6pRNASCoBOKtIshFeQd4XMUh'); const options = { mode: 'payment', amount: 1099, currency: 'usd', // Fully customizable with appearance API. appearance: { /*...*/ }, }; const App = () => ( <Elements stripe={stripePromise} options={options}> <CheckoutForm /> </Elements> ); ReactDOM.render(<App />, document.body); ``` 您可以閱讀[文件](https://github.com/stripe/react-stripe-js?tab=readme-ov-file#minimal-example)。 您幾乎可以整合任何東西。它有一個巨大的選項清單。 ![整合](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/67f3pb2i8xolt635rp2p.png) https://github.com/stripe --- 29. [Upscayl](https://github.com/upscayl/upscayl) - 開源 AI 影像升級器。 ---------------------------------------------------------------- ![高級](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2c1837rev5jb260ro2sd.png) 適用於 Linux、MacOS 和 Windows 的免費開源 AI Image Upscaler 採用 Linux 優先概念建構。 它可能與全端無關,但它對於升級圖像很有用。 ![高級](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/a4qq1wm3wey3vihn9al4.png) 透過最先進的人工智慧,Upscayl 可以幫助您將低解析度影像變成高解析度。清脆又鋒利! https://github.com/upscayl/upscayl --- 30.[重新發送](https://github.com/resend)- 為開發人員提供的電子郵件 API。 ------------------------------------------------------- ![重發](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/x3auhh3hbxjmmzehe5v0.png) 您可以使用 React 建立和傳送電子郵件。 2023 年最受炒作的產品之一。 開始使用以下 npm 指令。 ``` npm install @react-email/components -E ``` 這是將其與 next.js 專案整合的方法。 ``` import { EmailTemplate } from '@/components/email-template'; import { Resend } from 'resend'; const resend = new Resend(process.env.RESEND_API_KEY); export async function POST() { const { data, error } = await resend.emails.send({ from: '[email protected]', to: '[email protected]', subject: 'Hello world', react: EmailTemplate({ firstName: 'John' }), }); if (error) { return Response.json({ error }); } return Response.json(data); } ``` 您可以閱讀[文件](https://resend.com/docs/introduction)。 ![重發](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/rer9ym187e4i9l11afkg.png) 基本概念是一個簡單、優雅的介面,讓您可以在幾分鐘內開始發送電子郵件。它可以透過適用於您最喜歡的程式語言的 SDK 直接融入您的程式碼中。 https://github.com/resend --- 哇!如此長的專案清單。 我知道您有更多想法,分享它們,讓我們一起建造:D 如今建立全端應用程式並不難,但每個應用程式都可以透過有效地使用優秀的開源專案來解決任何問題來增加這一獨特因素。 例如,您可以建立一些提供通知或建立 UI 流來抓取資料的東西。 我希望其中一些內容對您的開發之旅有用。他們擁有一流的開發人員經驗;你可以依賴他們。 由於您將要建造東西,因此您可以在這裡找到一些[瘋狂的想法](https://github.com/florinpop17/app-ideas)。 祝你有美好的一天!直到下一次。 --- 原文出處:https://dev.to/copilotkit/im-building-a-full-stack-app-here-are-the-libraries-im-going-to-use-51nk

6 個 JavaScript 控制台方法,例如泰勒絲民間傳說歌詞

--- 標題:6 個 JavaScript 控制台方法,如泰勒絲民間傳說歌詞 發表:真實 描述:了解六種鮮為人知的 JavaScript 控制台方法,這些方法與泰勒絲 (Taylor Swift) 最新專輯《Followre》中的歌詞類似。 標籤: javascript、webdev、除錯、生產力 封面圖片:https://twilio-cms-prod.s3.amazonaws.com/images/ts\_AMVvYGp.width-1616.png --- 這篇部落格文章是為[Twilio](https://www.twilio.com/)撰寫的,[最初發佈在 Twilio 部落格上](https://www.twilio.com/blog/js-console-methods-like-taylor-swift-folklore-lyrics)。 如果您進行 Web 開發,您可能至少使用過一次`console.log` (或超過一千次...誰在數?),因為這是最好的偵錯方法!但您知道還有其他控制台方法嗎? Taylor Swift 的最新專輯《Followre》 充滿了沉思的隱喻、典故和象徵意義,這篇文章將其中一些歌詞比作 6 個鮮為人知的 JavaScript `console`方法。 ### 控制台到底是什麼? `console`是一個[全域物件](https://developer.mozilla.org/en-US/docs/Glossary/Global_object),允許開發人員存取偵錯控制台。它有大量的方法,可以更輕鬆地記錄語句、變數、函數、錯誤等——天哪! #### 6種類似民間傳說歌詞的控制台方法 #### *1. console.log = "但這會很有趣 // 如果你是那個人"* `console.log`是最常用的方法。用於通用日誌記錄,它在 Web 控制台中顯示傳遞給它的訊息。你知道你可以用 CSS 來裝飾它嗎? ``` console.log("%cWARNING: you will be obsessed with folklore", "font: 2em sans-serif; color: yellow; background-color: red;"); ``` ![輸出console.log css](https://twilio-cms-prod.s3.amazonaws.com/images/Yz6zzAsmqMlZsQPirgqJZ1U1MWR_pPvMUExuwPavf-Orm.width-1000.png) `Log`簡單、可靠,並且可以完成工作,但它被過度使用,吸引了類似`console`方法的所有註意力,這些方法做得更多。如果`Log`是您需要的一種或唯一的控制台方法,那麼它會很有趣 - 但正如本文將要展示的,您將透過其他`console`方法獲得更多樂趣! #### *2. console.table = "我是一個鏡球 // 今晚我會向你展示你自己的每個版本"* `table`方法接受一個物件或陣列並將輸入記錄為表格,使其看起來更乾淨:它就像`log`的更好版本。與鏡像球一樣, `table`可以透過接受可選參數`columns`來選擇要顯示的列子集來顯示不同版本的輸入。 陣列中的每個元素(如果資料是物件,則為每個可枚舉屬性)將是表中的一行。下面的 JavaScript 程式碼有一個物件,您可以看到最初使用 log 的輸出。 ``` function Album(name, year, numSongs) { this.name = name; this.year = year; this.numSongs = numSongs; } const fearless = new Album("Fearless", 2008, 13); const speakNow = new Album("Speak Now", 2010, 19); const folklore = new Album("folklore", 2020, 16); console.log([fearless, speakNow, folklore]); ``` ![物件的console.log](https://twilio-cms-prod.s3.amazonaws.com/images/4w8wxLh0fE0C0YQ1-lO-MdqRmLx_QjFj-ng-UcbM-C8Q2.width-1000.png) 這很好,但是給定陣列時`table`的輸出看起來更好: ``` console.table([fearless, speakNow, folklore]); ``` ![物件的console.table](https://twilio-cms-prod.s3.amazonaws.com/images/MqAnPKv4jrbZVF4Z7-vf37jkzC6N4ppYKS_-pFH0eXuov.width-1000.png) 接受`columns`參數,如`console.table([fearless, speakNow, folklore], ["name"]);`會顯示: ![帶有額外列參數的 console.table](https://twilio-cms-prod.s3.amazonaws.com/images/UTQQlcite2SYJZMXWuKc_p0yetEku7jPZLGtsmBc5aTGY.width-1000.png) 您也可以傳遞它(而不是`name` ) `year`或`numSongs` - 就像鏡子球一樣,表格可以向您顯示其輸入的每個版本! #### *3. console.assert =“如果你從不流血,你就永遠不會成長”* `console.assert(expression, message)`僅在表達式為 false 時才列印。泰勒絲 (Taylor Swift) 在歌曲*《The 1》*中的歌詞「如果你從不流血,你就永遠不會成長」也同意這一點——如果你從不流血,或者失敗,或者有時不正確,你就永遠不會成長。 `assert`表明,透過錯誤,您可以成長為一名開發人員,因為您可以修復錯誤,控制台會透過將斷言變成漂亮的紅色來幫助您。 ``` const numFolkloreSongs = 16; const num1989Songs = 13; console.assert(numFolkloreSongs > num1989Songs, 'folklore has more songs than 1989'); //won't run console.assert(num1989Songs + 3 > numFolkloreSongs, 'the number of songs on 1989 + 3 is not greater than the number of folklore songs'); ``` ![斷言失敗](https://twilio-cms-prod.s3.amazonaws.com/images/6kyCsGK8UWI0nEEgZ703RHjPu67krRq-OCmTgkDuiJtYw.width-1000.png) #### *4. console.time/console.timeEnd = "時間,神秘的時間/切開我,然後治癒我。"* `console.time()`建立一個計時器來查看某些操作需要多長時間。它可以採用名稱或標籤的可選參數來區分網頁上最多 10,000 個計時器。 `console.timeEnd()`停止計時器,並在控制台中顯示結果。 時間可能很艱難——它可以讓你心碎,但它也可以治癒你,讓你感覺更好。 ``` console.time('sms timer'); let x = 0; while (x < 3) { console.log("They told me all of my cages were mental/So I got wasted like all my potential"); x+=1; } console.timeEnd('sms timer'); ``` ![控制台時間](https://twilio-cms-prod.s3.amazonaws.com/images/C0ExSxgVLyLR6uuPM911Lhw64QJ3qLZXDWKbrLdJ5FwnD.width-1000.png) 如果沒有標籤傳遞給`console.time()` ,它將記錄 default 而不是*sms time* 。 #### *5. console.clear:“如果我對你來說已經死了,為什麼你還在守靈?”* `console.clear`簡短、甜蜜、簡潔。它會清除控制台,並且在某些環境中,可能會列印諸如“控制台已清除”之類的訊息。 歌詞“如果我對你來說已經死了,為什麼你還在守靈?”是憂鬱的,但也有一些尖銳的味道:它非常適合當你想要結束對話時,就像`clear`一樣,你可以重新開始,重新開始。 #### *6. console.group/console.groupEnd ="想到一直以來有一條看不見的繩子把你和我綁在一起,這不是很美好嗎?"* `console.group`表示內聯訊息群組的開始, `console.groupEnd`標記其結束。如果群組包含日誌,它們將作為一個群組列印,因此格式更清晰,您可以更輕鬆地了解群組包含的內容。 就像有一些看不見的字串(或`console`命令)將群組中的專案捆綁在一起。 ``` console.group("folklore"); console.log("the 1"); console.log("cardigan"); console.log("the last great american dynasty"); console.log("invisible string"); console.log("my tears ricochet"); console.groupEnd(); console.log("outside"); ``` ![團體](https://twilio-cms-prod.s3.amazonaws.com/images/JiqlDPAtBRz7G_ExfwKLEhsOXwAMZKIRS-Bv3YaL9SKGb.width-1000.png) #### 控制台的下一步是什麼? ![tswift 太棒了 gif](https://twilio-cms-prod.s3.amazonaws.com/original_images/tsgif.gif) 還有許多其他控制台方法未包含在此處(部分原因是它們與 Taylor Swift 歌詞的關係不大。)有關控制台方法的更多訊息,[請查看 Mozilla 開發者網絡有關 Web 技術的文件](https://developer.mozilla.org/en-US/docs/Web/API/console)。讓我知道您最喜歡或最不喜歡的民俗歌曲在線或在評論中! 1. 推特: [@lizziepika](https://twitter.com/lizziepika) 2. GitHub:[伊莉莎白西格爾](https://github.com/elizabethsiegle) 3. 電子郵件:[email protected] --- 原文出處:https://dev.to/twilio/6-javascript-console-methods-like-taylor-swift-folklore-lyrics-3h0k

真正去打造一樣幫助他人前進的東西,就不會失去動力

看到站長翻譯的[Ruby on Rails 之父:我怎麼學會寫程式的?](https://codelove.tw/@howtomakeaturn/post/k312Ya)這篇文章,想發表一點想法。 ## 真正的學習 我不是本科出身的,很長一段時間我都是亂無章法的自學。報名了一堆線上課程,也請過家教,甚至一度想要參加訓練營。但我一直都知道,那不適合我。 從架設第一個網站開始,我就有很「明確的問題」需要解決,所以一路上我幾乎都是「做中學」,問題在於,無人可以「糾正」我的錯誤,而錯誤不糾正,就難以進步。 所以我意識到我需要的不是尋找更好的課程,而是一個教練,一個可以糾正我的錯誤並引導我的教練,而不是手把手的教員。 教練很重要,教練的品格更重要,我無法把一個人的專業和他的品格分開(我找過不良品)。有些事情不能妥協,所以我才找到阿川。 DHH寫的這篇文章很簡短,我相信有很多「前後文」沒有提到。每個人的人生都有前後文,我們來自不同背景,或正在經歷不同的處境,我們都不是從零開始。 我們都被那些「學習神話」給洗腦了,如果有一種方式可以學會任何東西,那我想就是你那顆向學的「心」,而不是那些看起來很完美的學習路徑。 ## 為了重新學習美語發音,我開發了一個小工具 我正在重新學習美語發音,為了幫助和我一樣正在學習的人更好的練習,我開發了一個輔助的小工具,並藉此機會學習 JavaScript 這個程式語言。 這個小工具是根據[蕭博士](https://www.facebook.com/wen.hsiao.100)研發設計的PA注音符號表所建立,附上這張表的連結:https://drive.google.com/file/d/1mbxaL4yTAcJvWREeN179DAeQMgC2yCuK/view?usp=sharing 小工具中的注音符號卡,就是根據這張表的子音與母音的搭配所產生,我只是打亂出現的順序,作為學習者練習的輔助工具。下面附上這個小程式的連結: https://practicetool.github.io/ 歡迎各位前輩或同儕抓蟲或給我建議,我們一起學習。 - - - 我相信把心放到你的程式裡,就會產生動力。

💻Visual Studio Code 快捷指南、更高的生產力、以及您需要學習的 30 個快捷指令

介紹 == Visual Studio Code 允許您透過命令面板或鍵盤上的快捷鍵存取它提供的幾乎所有功能。 您可能每個工作日工作 8 小時,希望您能在這些工作時間中大部分時間進行編碼。所以你花了很多時間盯著你選擇的程式碼編輯器。 了解一些快捷方式可以幫助您更快地完成工作。知道如何更快地找到您需要的文件。您需要立即執行 NPM 命令,而不是開啟外部終端。 ![雙手在鍵盤上快速打字](https://media.giphy.com/media/eMxZ6lPl8dW9O/giphy.gif) 捷徑備忘單 ===== Visual Studio Code 的開發者 - [視窗](https://code.visualstudio.com/shortcuts/keyboard-shortcuts-windows.pdf) - [Linux](https://code.visualstudio.com/shortcuts/keyboard-shortcuts-linux.pdf) - [蘋果系統](https://code.visualstudio.com/shortcuts/keyboard-shortcuts-macos.pdf) 您可以下載這些備忘單,列印出來,然後將其放在辦公桌上以供快速參考,或嘗試在上班途中學習它們。不要試圖一次學會所有這些。這需要時間。所以要有耐心,你就會掌握它們。 鍵位圖 === 您是 Vim 用戶嗎?也許 Emacs 快捷方式已經刻在你的大腦裡了?或者,無論出於何種原因,您使用記事本++並欣賞記事本++的鍵盤快捷鍵😵? Visual Studio 為大家提供了一個擴充功能!讓我們安裝 ⚛ `Atom Keymap` 。我們將在沒有我們心愛的滑鼠的幫助下(幾乎)做到這一點。 1\) 開啟 Visual Studio 程式碼。 2\) Visual Studio Code 開啟後,按: `CTRL+SHIFT+X` 。該快捷方式將打開擴展列表,並且您的遊標將聚焦在搜尋欄上。輸入以下`@category:keymaps` 。 (如果您想了解更多有關本節中擴展程序如何工作的訊息,請在下面發表評論!) 3\) 您現在會看到鍵盤映射清單。按`Tab` ,然後按`Down Arrow ⬇` 。 4\) 按`⬇`直到選擇`Atom Keymap` 。現在按`Enter` 。 5)遺憾的是我找不到選擇「安裝」按鈕的方法。您現在需要點擊🖱! 您可以找到幾乎所有您能想像到的編輯器的鍵盤映射。安裝您最喜歡的那個,您就有了快捷方式!很酷吧? 鍵盤快速鍵設定 (JSON) ============== 有多種方法可以查看鍵盤快捷鍵設定。其中一種是透過圖形介面,也可以選擇使用透過 JSON 檔案來編輯捷徑。 圖形介面 ---- 我們可以按`CTRL+k`開啟圖形介面,然後仍然按住`CTRL` ,您應該按`CTRL+s` 。 ![鍵盤快捷鍵設定 GUI](https://thepracticaldev.s3.amazonaws.com/i/3etyosi4ljtp1d9lvk5i.png) 頂部有一個搜尋欄,您可以在其中搜尋要查看的命令或鍵盤快捷鍵。這些對話框在 Visual Studio Code 中看起來往往相同,您將開始經常看到它們。 您可以看到四列。讓我們來看看它們。 \*指令:Visual Studio Code 執行的操作。 - 鍵綁定:執行操作時必須按下的按鍵組合。 - 何時:這是 Visual Studio Code 的過濾器,它告訴 Visual Studio Code 捷徑是否應該在該上下文中可操作。有些過濾器可能是整合終端、原始碼中的錯誤等等。 - 來源:Visual Studio 程式碼可以透過多種方式了解捷徑。最常見的是`Default` ,這些命令是 Visual Studio Code 隨附的開箱即用命令。顧名思義`User`是由用戶建立的命令。第三種方式是透過`Extension` 。擴展作者還可以決定加入快捷方式。如果您最喜歡的快捷方式不起作用,這可能是它停止工作的原因。 若要變更鍵綁定,請雙擊該行,然後會彈出一個模式。然後按下所需的組合鍵並按下`Enter` 。 鍵綁定 JSON 文件 ----------- 現在我們知道了鍵綁定的一般工作原理,讓我們來看看`keybindings.json`檔案。 其中有兩個:預設的`keybindings.json`和使用者特定的`keybindings.json`檔案。按`CTRL+SHIFT+P`或`F1`開啟命令匣並鍵入`keyboard shortcuts`現在您應該在命令托盤中看到至少兩個條目。 - 首選項:開啟預設鍵盤快速鍵 (JSON)。 這是 Visual Studio Code 儲存所有預設快捷方式的文件,以及底部未使用的可用捷徑清單。我會避免在這裡更改它們。 - 首選項:開啟鍵盤快速鍵 (JSON) 這是用戶特定的鍵綁定文件,您應該編輯此文件。一開始,它只是一個空陣列而已! 要在 JSON 檔案中新增快捷方式,您只需新增一個如下所示的物件: ``` [ { "key": "CTRL+ALT+P", "command": "git.pull", "when": "" } ] ``` 您需要指定密鑰和命令。 `when`告訴 Visual Studio Code 應在何處執行此命令。如果你把它留空,它會到處監聽。我們在上一部分談到了這一點。 有用的快捷鍵 ====== 打開命令面板 ------ 您已經知道這一點,但也許您跳到了這一部分 😉 - `CRTL+SHIFT+P`或`F1` 這將開啟 Visual Studio Code 中最強大的功能。命令面板。只需輸入您認為想要的內容,它仍然可以找到它! 打開和關閉側邊欄 -------- 有時您想要更多的水平空間,但側邊欄卻妨礙了您!只需按 - `CTRL+B` 您可以打開和關閉側邊欄 輸入禪宗模式 ------ 你喜歡 Visual Studio 程式碼中的 Zen Mod 嗎?是的,它是內建的! 為此,您需要按: - `CTRL+k` ,放開兩個按鍵並按`z` 。 這將打開和關閉 Zen Mod。 聚焦綜合終端 ------ 我最喜歡的功能之一是 Visual Studio Code 中的整合終端機。我99%的時間都在用它!因此要快速打開或關閉它,您需要按: - `CTRL+j` 這將打開整合終端並將遊標聚焦在其中。如果您再次按下它,它將關閉,並且您的遊標將返回到原來的位置。 在您的專案中搜尋文件 ---------- Visual Studio Code 有一個很棒的檔案搜尋內建功能。當您使用遠端擴展時,它也非常快。要打開它,您只需按: - `CTRL+p` 這將打開一個對話框,您可以在其中查看最近打開的文件,這本身就非常好。它還支援模糊搜尋。這意味著您可以鍵入任何單字,它會在檔案的路徑中找到。所以你不必精確!該對話還支持更多的事情。例如`go-to line`或除錯以及更多功能!如果您想了解更多請在下面評論。 切換到最近開啟的工作區 ----------- 您在微服務架構中工作並且需要一直切換資料夾?因為你不使用 mono 倉庫?我有捷徑給你!按: - `CTRL+r` 這將開啟一個對話框,其中包含最近開啟的工作區/資料夾的清單。 額外提示:如果您在該對話方塊中按`CTRL+ENTER` Visual Studio Code 將在新視窗中開啟它。 分割編輯器視窗 ------- 人們喜歡 vim,因為它很容易在編輯器之間分割視圖。 Visual Studio Code 也內建了功能。只需按 - `CTRL+\` 若要建立 2 列或 - `CTRL+k` ,放開`k`並按住`CTRL`並按`\` 建立一個新行。第二個聽起來比它更難,但是一旦它進入你的大腦,它需要你幾秒鐘的時間,你現在知道如何更改或建立新的快捷方式😉 聚焦編輯器視窗 ------- 既然您知道如何拆分編輯器窗口,您還需要學習如何快速跳轉這些視圖。這非常簡單,並且還有預設的鍵綁定。你需要按 - `CTRL+[1-9]` 這表示您需要按`CTRL`加您想要關注的視窗的編號。對於第一個視窗按`CTRL+1` ,第二個視窗`CTRL+2` ,您明白了 Easy 的想法嗎? 關閉目前編輯器視窗 --------- 現在您打開了太多編輯器窗口,並且您想要關閉它們。這可以透過按快速完成 - `CTRL+w` 這將關閉目前開啟的視窗。 僅關閉已儲存的編輯器視窗 ------------ 有時您會開啟如此多的編輯器,以至於您不再知道要儲存了什麼。是的,我知道您可以透過選項卡欄中的那個點看到這一點,但是,您仍然無法集中精力並找到正確的檔案。 Visual Studio Code 為您提供支援!只需按 - `CTRL+k`然後放開`CTRL`和`k`並按`u` 這將保存所有窗口,以便您可以檢查未保存的窗口並保存它們。 開啟一個新文件 ------- 您需要一個新檔案來繪製一些程式碼嗎?或者,您需要為您的寵物專案建立一個新檔案?按 - `CTRL+n` 這將開啟一個新編輯器。 更改目前文件的語言 --------- 您想切換目前文件中選定的語言,因為您想要`Javascript (react)`而不是`Javascript` ?按 - `CTRL+k` 然後放開`CTRL`和`k`並按 'm`。 這將打開一個新的對話,您可以在其中搜尋所需的語言。 前往線路 ---- 現在讓我們專注於如何讓編輯變得更容易。第 1042 行有錯誤(如果您的文件那麼長,那麼問題就來了)。你不想滾動!按 - `CTRL+g` 這將開啟一個對話框,您需要輸入要跳到的行號。與`CTRL+p`結合使用會非常強大。 轉到符號 ---- 您的第一個問題是,什麼是符號?在程式語言中,符號通常是變數。在 CSS 中,它們是選擇器。若要查看對話,請按 - `CTRL+SHIFT+O` 這將開啟一個對話框,其中包含目前文件中可用符號的清單。 - `CTRL+t` 您會看到一個只有`#`的對話框,您需要鍵入所需的符號,Visual Studio Code 會在空工作區中搜尋該符號(如果您使用的語言支援該符號)。所以你需要自己檢查一下。 向上或向下移動一條線。 ----------- 有時您需要移出`if`內的那行程式碼,或只是移動一行,因為它被提前呼叫了。您可以透過按 - `Alt+Down` 將目前選定的行向下移動一行 - `Alt+Up` 將目前選定的行向上移動一行 複製目前行 ----- 您想用一些變數填充該陣列,但您懶得寫一個循環。那麼要如何填滿`array[0]` `array[1]`和`array[2]`呢?透過複製第一行兩次並僅更改您需要的內容。對於那個新聞界 - `ALT+SHIFT+Up` 這將複製當前選定的行並將其貼上到上面的一行中 - `ALT+SHIFT+Down` 這將複製目前選定的行並將其貼上到下面的一行中 (這個快捷方式在這裡會很方便) 顯示建議 ---- Visual Studio Code 有內建建議。大多數時候它會自動為您彈出,但有時不會,而您確實需要它。簡單,按 - `CTRL+Spacebar` 這將打開建議對話框 註解掉目前選擇 ------- 有時您需要隔離程式碼並註解掉它周圍的所有內容。按 - `CTRL+/` 如果您選擇了多行,則會將其註解掉。如果您沒有選擇任何內容,它只會註解掉這一行。 選擇多行程式碼 ------- 要註解掉該程式碼區塊,您需要選擇多行。這是透過按完成的 - `CTRL+Shift+Up` 從目前行開始選擇並向上移動遊標。 - `CTRL+Shift+down` 從目前行開始選擇並向下移動遊標。 折疊和展開您的程式碼 ---------- 你有這麼大的功能,但你真的看不到它了,因為它太大了,需要重構,但你沒有時間,所以你想忘記它嗎?您可以折疊和展開程式碼,以便在 100 行中可以產生 1 行。若要執行此操作,請按 - `CTRL+SHIFT+[` 折疊(隱藏)程式碼 - `CTRL+SHIFT+]` 展開(顯示)程式碼 切一條孔線 ----- 對於此,您不能選擇任何程式碼。按 - `CTRL+x` 當沒有選擇任何內容時,這會剪切整行。 縮排/減少線 ------ 人們通常知道如何縮排程式碼。您可以選擇要縮排的程式碼並按 - `Tab` 按下您想要的次數按 Tab 鍵,這樣效果就適合您了。 您知道可以取消縮排嗎?將程式碼從右移到左?您可以透過按 - `SHIFT+tab` 結論 == 還有更多的捷徑。這些快捷鍵是我最常使用的快捷鍵。我希望這可以幫助您更多地了解 Visual Studio Code 中的快捷方式,並且您現在可以建立自己的快捷方式。 我是否忽略了每個人都需要知道的有用命令? 你錯過了什麼嗎?有什麼不清楚嗎? 請寫評論。我盡我所能回答你所有的問題! **👋問好!** [Instagram](https://www.instagram.com/lampewebdev/) |[推特](https://twitter.com/lampewebdev)|[領英](https://www.linkedin.com/in/michael-lazarski-25725a87)|[中等](https://medium.com/@lampewebdevelopment)|[抽搐](https://dev.to/twitch_live_streams/lampewebdev)| [Youtube](https://www.youtube.com/channel/UCYCe4Cnracnq91J0CgoyKAQ) --- 原文出處:https://dev.to/lampewebdev/the-guide-to-visual-studio-code-shortcuts-higher-productivity-and-30-of-my-favourite-shortcuts-you-need-to-learn-mb3

使用 VS Code 在 JavaScript 專案中設定 ESLINT

*ESLINT* :你有沒有想過ESLINT 是什麼,當我第一次聽說ESLINT 時,我很好奇它到底是怎麼回事,從那時起我就一直在我的專案中使用它,儘管一開始我錯誤地使用了它,那就是為什麼我發布這篇文章是為了讓人們能夠正確理解。但在深入探討之前,讓我先快速解釋一下什麼是 ESLINT 和 VS Code。 **ESLINT**是用於 Javascript 和 JSX 的可插入 linting 實用程序,它有助於發現可能的錯誤。 **VS Code**是頂級的開發編輯器之一,它由 Microsoft 開發和維護,它有助於提高生產力,並且還具有許多功能,我要強調的功能之一是擴充。擴充功能是 VS Code 中的外部套件,可讓您擴展編輯器的功能 你可以從他們的官方網站下載 VS Code [VS Code Download](https://code.visualstudio.com/) **注意:***我不會深入研究 VS Code。本文中有關 VS Code 的所有內容都只與 ESLINT 相關*。 **腳步**: - 建立一個 JavaScript 專案 - 在 VS Code 編輯器中安裝 eslint 作為擴展 - 使用 npm 將 eslint 安裝為全域包 - 在您的 javascript 專案中初始化 eslint - 修改專案中的 eslint 設定檔。 讓我們使用`npm init --yes`建立一個簡單的 javascript 專案 ![alt text](https://thepracticaldev.s3.amazonaws.com/i/tebfsgkfr3k3h4bl7zvr.PNG "簡單的專案") 操作成功後,它將建立一個*package.json*文件,該文件將管理我們專案的所有配置。 讓我們嘗試在 VS Code 編輯器上安裝 ESLINT 擴充 ![alt text](https://thepracticaldev.s3.amazonaws.com/i/9rmkgbk7nio6ravjm0rx.PNG "ESLINT安裝過程") 一旦我們在 VS Code 編輯器上安裝了 eslint 擴展,然後使用下面的程式碼透過 npm 將 eslint 安裝為全域包 ``` npm install eslint -g ``` 您需要在專案中初始化 eslint,以便可以利用 eslint 的強大功能。從您的根專案輸入以下程式碼來初始化 eslint ``` eslint --init ``` 在初始化期間 eslint 會問你一些問題,更像是設定你的設定檔。 - **您想如何使用 ESLint?** ``` * __To check syntax only__ => it helps you correct your syntax and make sure it conform to standard. ``` ``` * __To check syntax and find problems__ => to help you check for syntax correctness and also help to find any problems in your code base ``` ``` * __To check syntax, find problems, and enforce code style___ => to help you check for syntax, find problem and enforce style, enforcing style means to conforms to a particular coding standard such as Airbnb, Google and other Standard coding style. But I always go for the last option the one with syntax, find problems and enforce code style ``` - **您的專案使用什麼類型的模組?** ``` * __Javascript module (import/export)__ => if your project has babel installed then you definitely need to choose this option. If you are working on a project such as React, Vue, Angular e.t.c they all use babel so you need choose this option. ``` ``` * __CommonJS (require/exports)__ => this option is meant for commonJS that has nothing to do with babel, maybe your nodejs project and any other javascript project ``` - **您的專案使用哪個框架?** ``` * __React__ => if you are using react in/for your project then this option is for you ``` ``` * __Vue__ => if you are using Vue in/for your project then this option is for you ``` ``` * __None of these__ => if you are using neither React or Vue in your project choose this option ``` - **你的程式碼在哪裡執行?** ``` * __Browser__ => if your project runs on browser e.g React, Angular, Vue e.t.c then go for this option ``` ``` * __Node__ => if your project is a node based then gladly choose this option ``` - **您希望如何為您的專案定義風格?** ``` * __Use a popular style guide__ => This allows you to choose from set of popular style such as Airbnb,Standard and Google style guide, it is advisable to choose this option in order for you to follow popular and most used style guide and i will be choosen this option in this post. ``` ``` * Answer questions about your style: _This is for custom style guide_ ``` ``` * Inspect your JavaScript file(s).: _custom style guide_ ``` - **您希望設定檔採用什麼格式?** ``` * __Javascript__ => whether you want your eslint config file to be in *.js* file ``` ``` * __YAML__ => whether you want your eslint config file to be in *.yaml* file ``` ``` * __JSON__ => whether you want your eslint config file to be in *.json* file ``` 您可以選擇此部分中的任何選項 選擇首選設定檔類型後,它將提示您安裝所有必要的依賴項。成功安裝所有必要的依賴項後,它將產生一個帶有“.eslintrc”.“js/json/yaml”的設定檔。 **如下所示的設定檔範例** ![alt text](https://thepracticaldev.s3.amazonaws.com/i/sqyim5m8qoet5lx4bu8o.PNG "eslint設定檔鏡像") 下面是一個小動畫圖像,顯示 VS Code 如何與 eslint 配合使用來通知您 javascript 專案中的錯誤 ![alt text](https://cdn-images-1.medium.com/max/800/1*udUEME0YgHCXqD4pjMxpUA.gif "eslint設定檔鏡像") **在專案中設定 ESLINT 規則** 在專案中定義 ESLINT 規則會告知 eslint 您要新增或刪除的規則類型。您可以在設定檔的規則部分修改/設定規則 要設定的規則範例是 ``` "rules" : { no-console: 0; no-empty: 0; no-irregular-whitespace:0; } ``` 您可以定義盡可能多的規則,您可以在其官方文件[ESLINT Rules Documentation](https://eslint.org/docs/rules/)上閱讀有關 ESLINT 規則的更多訊息 最後,我將向您展示如何將 eslint 連結到 javascript 專案編譯器/轉譯器 以下步驟 - 前往`package.json`文件,在文件的腳本段中加入以下內容 ``` script:{ "lint":"eslint" } ``` **注意:** *“lint”只是一個普通單詞,您可以使用任何您喜歡的單詞* 然後在你的根專案中你可以執行你的 linting 腳本 ``` npm run lint ``` > ESLINT 有助於提高工作效率,根據標準編寫程式碼,並在您的程式碼庫違反樣式指南規則時標記錯誤。透過這篇文章,您應該能夠將 ESLINT 整合到您的 Javascript 專案中。 --- 原文出處:https://dev.to/devdammak/setting-up-eslint-in-your-javascript-project-with-vs-code-2amf

9 個極為強大的 JavaScript Hack

我喜歡優化。 但如果網站無法在 Internet Explorer 11 瀏覽器中執行,用戶不會關心我的優化程式碼。 我使用**[Endtest](https://endtest.io)**建立自動化測試並在跨瀏覽器雲端上執行它們。 **[Netflix](https://jobs.lever.co/netflix/db335e29-c731-42ff-ad3a-eeecbe95b36f)**使用相同的平台來測試他們的網路應用程式。 它甚至被列為某些**[工作](https://www.linkedin.com/jobs/view/1486749071/)**的必備技能。 **[Endtest](https://endtest.io)**確實有一些非常好的功能,例如: • 跨瀏覽器網格,在 Windows 和 macOS 電腦上執行 • 用於自動化測試的無程式碼編輯器 • 支援網頁應用程式 • 支援本機和混合Android 和iOS 應用程式 • 用於測試執行的無限視訊錄製 • 螢幕截圖比較 • 地理位置 • If 語句 • 循環 • 在測試中上傳文件 • Endtest API,可輕鬆與您的 CI/CD 系統集成 • 進階斷言 • 在真實行動裝置上進行行動測試 • 使用 Endtest Mailbox 進行電子郵件測試 您應該查看**[文件](https://endtest.io/guides/docs/how-to-create-web-tests/)**。 以下是 9 個極為強大的 JavaScript 技巧。 **1.全部替換** ---------- 我們知道 string.replace() 函數僅取代第一次出現的位置。 您可以透過在正規表示式末尾新增 /g 來取代所有出現的情況。 ``` var example = "potato potato"; console.log(example.replace(/pot/, "tom")); // "tomato potato" console.log(example.replace(/pot/g, "tom")); // "tomato tomato" ``` **2. 提取唯一的值** -------------- 我們可以使用 Set 物件和 Spread 運算子建立一個僅具有唯一值的新陣列。 ``` var entries = [1, 2, 2, 3, 4, 5, 6, 6, 7, 7, 8, 4, 2, 1] var unique_entries = [...new Set(entries)]; console.log(unique_entries); // [1, 2, 3, 4, 5, 6, 7, 8] ``` **3. 將數字轉換為字串** --------------- 我們只需使用帶有一組空引號的串聯運算子即可。 ``` var converted_number = 5 + ""; console.log(converted_number); // 5 console.log(typeof converted_number); // string ``` **4. 將字串轉換為數字** --------------- 我們需要的只是 + 運算子。 請小心這一點,因為它僅適用於“字串數字”。 ``` the_string = "123"; console.log(+the_string); // 123 the_string = "hello"; console.log(+the_string); // NaN ``` **5. 隨機排列陣列中的元素** ----------------- **我每天都在洗牌** ``` var my_list = [1, 2, 3, 4, 5, 6, 7, 8, 9]; console.log(my_list.sort(function() { return Math.random() - 0.5 })); // [4, 8, 2, 9, 1, 3, 6, 5, 7] ``` **6. 展平多維陣列** ------------- 只需使用 Spread 運算子即可。 ``` var entries = [1, [2, 5], [6, 7], 9]; var flat_entries = [].concat(...entries); // [1, 2, 5, 6, 7, 9] ``` **7. 短路條件** ----------- 讓我們來看這個例子: ``` if (available) { addToCart(); } ``` 並通過簡單地將變數與函數一起使用來縮短它: ``` available && addToCart() ``` **8. 動態屬性名稱** ------------- 我一直認為我必須先聲明一個物件,然後才能指派動態屬性。 ``` const dynamic = 'flavour'; var item = { name: 'Coke', [dynamic]: 'Cherry' } console.log(item); // { name: "Coke", flavour: "Cherry" } ``` **9. 使用 length 調整陣列大小/清空陣列** ---------------------------- 我們基本上覆蓋了陣列的長度。 如果我們想要調整陣列的大小: ``` var entries = [1, 2, 3, 4, 5, 6, 7]; console.log(entries.length); // 7 entries.length = 4; console.log(entries.length); // 4 console.log(entries); // [1, 2, 3, 4] ``` 如果我們想清空陣列: ``` var entries = [1, 2, 3, 4, 5, 6, 7]; console.log(entries.length); // 7 entries.length = 0; console.log(entries.length); // 0 console.log(entries); // [] ``` 我認為您正在尋找 JavaScript hack 真的很酷,但是您確定您的 Web 應用程式可以在所有瀏覽器和裝置上正常運作嗎? 您可以使用**[Endtest](https://endtest.io)**快速建立自動化測試並在跨瀏覽器雲端上執行它們。 您甚至無需編寫程式碼即可使用它。 說真的,只需閱讀**[文件](https://endtest.io/guides/docs/how-to-create-web-tests/)**即可。 --- 原文出處:https://dev.to/razgandeanu/9-extremely-powerful-javascript-hacks-4g3p