Removed tailwindcss/typo and use custom class instead
This commit is contained in:
		
							parent
							
								
									35c889d389
								
							
						
					
					
						commit
						8de571a030
					
				
							
								
								
									
										50
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										50
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							| @ -20,7 +20,6 @@ | ||||
|         "turndown": "^7.1.1" | ||||
|       }, | ||||
|       "devDependencies": { | ||||
|         "@tailwindcss/typography": "^0.5.2", | ||||
|         "@types/node": "17.0.21", | ||||
|         "@types/react": "17.0.40", | ||||
|         "@types/react-dom": "^17.0.13", | ||||
| @ -455,20 +454,6 @@ | ||||
|       "integrity": "sha512-JLo+Y592QzIE+q7Dl2pMUtt4q8SKYI5jDrZxrozEQxnGVOyYE+GWK9eLkwTaeN9DDctlaRAQ3TBmzZ1qdLE30A==", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "node_modules/@tailwindcss/typography": { | ||||
|       "version": "0.5.2", | ||||
|       "resolved": "https://registry.npmjs.org/@tailwindcss/typography/-/typography-0.5.2.tgz", | ||||
|       "integrity": "sha512-coq8DBABRPFcVhVIk6IbKyyHUt7YTEC/C992tatFB+yEx5WGBQrCgsSFjxHUr8AWXphWckadVJbominEduYBqw==", | ||||
|       "dev": true, | ||||
|       "dependencies": { | ||||
|         "lodash.castarray": "^4.4.0", | ||||
|         "lodash.isplainobject": "^4.0.6", | ||||
|         "lodash.merge": "^4.6.2" | ||||
|       }, | ||||
|       "peerDependencies": { | ||||
|         "tailwindcss": ">=3.0.0 || >= 3.0.0-alpha.1 || insiders" | ||||
|       } | ||||
|     }, | ||||
|     "node_modules/@types/json5": { | ||||
|       "version": "0.0.29", | ||||
|       "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", | ||||
| @ -2405,18 +2390,6 @@ | ||||
|         "node": ">=4" | ||||
|       } | ||||
|     }, | ||||
|     "node_modules/lodash.castarray": { | ||||
|       "version": "4.4.0", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.castarray/-/lodash.castarray-4.4.0.tgz", | ||||
|       "integrity": "sha1-wCUTUV4wna3dTCTGDP3c9ZdtkRU=", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "node_modules/lodash.isplainobject": { | ||||
|       "version": "4.0.6", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", | ||||
|       "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "node_modules/lodash.merge": { | ||||
|       "version": "4.6.2", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", | ||||
| @ -3950,17 +3923,6 @@ | ||||
|       "integrity": "sha512-JLo+Y592QzIE+q7Dl2pMUtt4q8SKYI5jDrZxrozEQxnGVOyYE+GWK9eLkwTaeN9DDctlaRAQ3TBmzZ1qdLE30A==", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "@tailwindcss/typography": { | ||||
|       "version": "0.5.2", | ||||
|       "resolved": "https://registry.npmjs.org/@tailwindcss/typography/-/typography-0.5.2.tgz", | ||||
|       "integrity": "sha512-coq8DBABRPFcVhVIk6IbKyyHUt7YTEC/C992tatFB+yEx5WGBQrCgsSFjxHUr8AWXphWckadVJbominEduYBqw==", | ||||
|       "dev": true, | ||||
|       "requires": { | ||||
|         "lodash.castarray": "^4.4.0", | ||||
|         "lodash.isplainobject": "^4.0.6", | ||||
|         "lodash.merge": "^4.6.2" | ||||
|       } | ||||
|     }, | ||||
|     "@types/json5": { | ||||
|       "version": "0.0.29", | ||||
|       "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", | ||||
| @ -5394,18 +5356,6 @@ | ||||
|         "path-exists": "^3.0.0" | ||||
|       } | ||||
|     }, | ||||
|     "lodash.castarray": { | ||||
|       "version": "4.4.0", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.castarray/-/lodash.castarray-4.4.0.tgz", | ||||
|       "integrity": "sha1-wCUTUV4wna3dTCTGDP3c9ZdtkRU=", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "lodash.isplainobject": { | ||||
|       "version": "4.0.6", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", | ||||
|       "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=", | ||||
|       "dev": true | ||||
|     }, | ||||
|     "lodash.merge": { | ||||
|       "version": "4.6.2", | ||||
|       "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", | ||||
|  | ||||
| @ -22,7 +22,6 @@ | ||||
|     "turndown": "^7.1.1" | ||||
|   }, | ||||
|   "devDependencies": { | ||||
|     "@tailwindcss/typography": "^0.5.2", | ||||
|     "@types/node": "17.0.21", | ||||
|     "@types/react": "17.0.40", | ||||
|     "@types/react-dom": "^17.0.13", | ||||
|  | ||||
| @ -1,6 +1,9 @@ | ||||
| import HorizontalLine from "components/HorizontalLine"; | ||||
| import InsetBox from "components/InsetBox"; | ||||
| import { useAppLayout } from "contexts/AppLayoutContext"; | ||||
| import Markdown from "markdown-to-jsx"; | ||||
| import SceneBreak from "./SceneBreak"; | ||||
| import { slugify } from "queries/helpers"; | ||||
| import React from "react"; | ||||
| 
 | ||||
| type ScenBreakProps = { | ||||
|   className?: string; | ||||
| @ -9,15 +12,31 @@ type ScenBreakProps = { | ||||
| 
 | ||||
| export default function Markdawn(props: ScenBreakProps): JSX.Element { | ||||
|   const appLayout = useAppLayout(); | ||||
|   const text = preprocessMarkDawn(props.text); | ||||
| 
 | ||||
|   if (props.text) { | ||||
|   if (text) { | ||||
|     return ( | ||||
|       <Markdown | ||||
|         className={`prose prose-p:text-justify text-black ${props.className}`} | ||||
|         className={`formatted ${props.className}`} | ||||
|         options={{ | ||||
|           slugify: slugify, | ||||
|           overrides: { | ||||
|             hr: { | ||||
|               component: SceneBreak, | ||||
|             Sep: { | ||||
|               component: () => { | ||||
|                 return <div className="my-24"></div>; | ||||
|               }, | ||||
|             }, | ||||
|             SceneBreak: { | ||||
|               component: (props: { id: string }) => { | ||||
|                 return ( | ||||
|                   <div | ||||
|                     id={props.id} | ||||
|                     className={"h-0 text-center text-3xl text-dark mt-16 mb-20"} | ||||
|                   > | ||||
|                     * * * | ||||
|                   </div> | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|             player: { | ||||
|               component: () => { | ||||
| @ -28,12 +47,80 @@ export default function Markdawn(props: ScenBreakProps): JSX.Element { | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|             Transcript: { | ||||
|               component: (props) => { | ||||
|                 return ( | ||||
|                   <div className="grid grid-cols-[auto_1fr] gap-x-6 gap-y-2"> | ||||
|                     {props.children} | ||||
|                   </div> | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|             Line: { | ||||
|               component: (props) => { | ||||
|                 return ( | ||||
|                   <> | ||||
|                     <strong className="text-dark opacity-60"> | ||||
|                       {props.name} | ||||
|                     </strong> | ||||
|                     <p className="whitespace-pre-line">{props.children}</p> | ||||
|                   </> | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|             InsetBox: { | ||||
|               component: (props) => { | ||||
|                 return <InsetBox>{props.children}</InsetBox>; | ||||
|               }, | ||||
|             }, | ||||
|             li: { | ||||
|               component: (props: { children: React.ReactNode }) => { | ||||
|                 return ( | ||||
|                   <li | ||||
|                     className={ | ||||
|                       props.children && props.children?.toString().length > 100 | ||||
|                         ? "my-4" | ||||
|                         : "" | ||||
|                     } | ||||
|                   > | ||||
|                     {props.children} | ||||
|                   </li> | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|             Highlight: { | ||||
|               component: (props: { children: React.ReactNode }) => { | ||||
|                 return <mark>{props.children}</mark>; | ||||
|               }, | ||||
|             }, | ||||
|             footer: { | ||||
|               component: (props: { children: React.ReactNode }) => { | ||||
|                 return ( | ||||
|                   <> | ||||
|                     <HorizontalLine /> | ||||
|                     <div>{props.children}</div> | ||||
|                   </> | ||||
|                 ); | ||||
|               }, | ||||
|             }, | ||||
|           }, | ||||
|         }} | ||||
|       > | ||||
|         {props.text} | ||||
|         {text} | ||||
|       </Markdown> | ||||
|     ); | ||||
|   } | ||||
|   return <></>; | ||||
| } | ||||
| 
 | ||||
| export function preprocessMarkDawn(text: string): string { | ||||
|   let scenebreakIndex = 0; | ||||
|   const result = text.split("\n").map((line) => { | ||||
|     if (line === "* * *" || line === "---") { | ||||
|       scenebreakIndex++; | ||||
|       return `<SceneBreak id="scene-break-${scenebreakIndex}">`; | ||||
|     } | ||||
|     return line; | ||||
|   }); | ||||
|   return result.join("\n"); | ||||
| } | ||||
|  | ||||
| @ -1,15 +0,0 @@ | ||||
| type ScenBreakProps = { | ||||
|   className?: string; | ||||
| }; | ||||
| 
 | ||||
| export default function SceneBreak(props: ScenBreakProps): JSX.Element { | ||||
|   return ( | ||||
|     <div | ||||
|       className={ | ||||
|         "h-0 text-center text-3xl text-dark mt-16 mb-20" + " " + props.className | ||||
|       } | ||||
|     > | ||||
|       * * * | ||||
|     </div> | ||||
|   ); | ||||
| } | ||||
							
								
								
									
										153
									
								
								src/components/Markdown/TOC.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										153
									
								
								src/components/Markdown/TOC.tsx
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,153 @@ | ||||
| import { slugify } from "queries/helpers"; | ||||
| import { preprocessMarkDawn } from "./Markdawn"; | ||||
| 
 | ||||
| type TOCProps = { | ||||
|   text: string; | ||||
|   title?: string; | ||||
| }; | ||||
| 
 | ||||
| export default function TOC(props: TOCProps): JSX.Element { | ||||
|   const toc = getTocFromMarkdawn(preprocessMarkDawn(props.text), props.title); | ||||
| 
 | ||||
|   return ( | ||||
|     <div> | ||||
|       <h3 className="text-xl">Table of content</h3> | ||||
|       <ol className="text-left"> | ||||
|         <li className="my-2 overflow-x-hidden w-full text-ellipsis whitespace-nowrap"> | ||||
|           <a className="" href={`#${toc.slug}`}> | ||||
|             {<abbr title={toc.title}>{toc.title}</abbr>} | ||||
|           </a> | ||||
|         </li> | ||||
|         {toc.children.map((h2, h2Index) => ( | ||||
|           <> | ||||
|             <li | ||||
|               key={h2.slug} | ||||
|               className="my-2 overflow-x-hidden w-full text-ellipsis whitespace-nowrap" | ||||
|             > | ||||
|               <span className="text-dark">{`${h2Index + 1}. `}</span> | ||||
|               <a href={`#${h2.slug}`}> | ||||
|                 {<abbr title={h2.title}>{h2.title}</abbr>} | ||||
|               </a> | ||||
|             </li> | ||||
|             <ol className="pl-4 text-left"> | ||||
|               {h2.children.map((h3, h3Index) => ( | ||||
|                 <li | ||||
|                   key={h3.slug} | ||||
|                   className="my-2 overflow-x-hidden w-full text-ellipsis whitespace-nowrap" | ||||
|                 > | ||||
|                   <span className="text-dark">{`${h2Index + 1}.${ | ||||
|                     h3Index + 1 | ||||
|                   }. `}</span>
 | ||||
|                   <a href={`#${h3.slug}`}> | ||||
|                     {<abbr title={h3.title}>{h3.title}</abbr>} | ||||
|                   </a> | ||||
|                 </li> | ||||
|               ))} | ||||
|             </ol> | ||||
|           </> | ||||
|         ))} | ||||
|       </ol> | ||||
|     </div> | ||||
|   ); | ||||
| } | ||||
| 
 | ||||
| export type TOC = { | ||||
|   title: string; | ||||
|   slug: string; | ||||
|   children: TOC[]; | ||||
| }; | ||||
| 
 | ||||
| export function getTocFromMarkdawn(text: string, title?: string): TOC { | ||||
|   if (!title) title = "Return to top"; | ||||
|   let toc: TOC = { title: title, slug: slugify(title) || "", children: [] }; | ||||
|   let h2 = -1; | ||||
|   let h3 = -1; | ||||
|   let h4 = -1; | ||||
|   let h5 = -1; | ||||
|   let scenebreak = 0; | ||||
|   let scenebreakIndex = 0; | ||||
|   text.split("\n").map((line) => { | ||||
|     if (line.startsWith("# ")) { | ||||
|       toc.slug = slugify(line); | ||||
|     } else if (line.startsWith("## ")) { | ||||
|       toc.children.push({ | ||||
|         title: line.slice("## ".length), | ||||
|         slug: slugify(line), | ||||
|         children: [], | ||||
|       }); | ||||
|       h2++; | ||||
|       h3 = -1; | ||||
|       h4 = -1; | ||||
|       h5 = -1; | ||||
|       scenebreak = 0; | ||||
|     } else if (line.startsWith("### ")) { | ||||
|       toc.children[h2].children.push({ | ||||
|         title: line.slice("### ".length), | ||||
|         slug: slugify(line), | ||||
|         children: [], | ||||
|       }); | ||||
|       h3++; | ||||
|       h4 = -1; | ||||
|       h5 = -1; | ||||
|       scenebreak = 0; | ||||
|     } else if (line.startsWith("#### ")) { | ||||
|       toc.children[h2].children[h3].children.push({ | ||||
|         title: line.slice("#### ".length), | ||||
|         slug: slugify(line), | ||||
|         children: [], | ||||
|       }); | ||||
|       h4++; | ||||
|       h5 = -1; | ||||
|       scenebreak = 0; | ||||
|     } else if (line.startsWith("##### ")) { | ||||
|       toc.children[h2].children[h3].children[h4].children.push({ | ||||
|         title: line.slice("##### ".length), | ||||
|         slug: slugify(line), | ||||
|         children: [], | ||||
|       }); | ||||
|       h5++; | ||||
|       scenebreak = 0; | ||||
|     } else if (line.startsWith("###### ")) { | ||||
|       toc.children[h2].children[h3].children[h4].children[h5].children.push({ | ||||
|         title: line.slice("###### ".length), | ||||
|         slug: slugify(line), | ||||
|         children: [], | ||||
|       }); | ||||
|     } else if (line.startsWith(`<SceneBreak`)) { | ||||
|       scenebreak++; | ||||
|       scenebreakIndex++; | ||||
|       if (h5 >= 0) { | ||||
|         toc.children[h2].children[h3].children[h4].children[h5].children.push({ | ||||
|           title: `Scene break ${scenebreak}`, | ||||
|           slug: slugify(`scene-break-${scenebreakIndex}`), | ||||
|           children: [], | ||||
|         }); | ||||
|       } else if (h4 >= 0) { | ||||
|         toc.children[h2].children[h3].children[h4].children.push({ | ||||
|           title: `Scene break ${scenebreak}`, | ||||
|           slug: slugify(`scene-break-${scenebreakIndex}`), | ||||
|           children: [], | ||||
|         }); | ||||
|       } else if (h3 >= 0) { | ||||
|         toc.children[h2].children[h3].children.push({ | ||||
|           title: `Scene break ${scenebreak}`, | ||||
|           slug: slugify(`scene-break-${scenebreakIndex}`), | ||||
|           children: [], | ||||
|         }); | ||||
|       } else if (h2 >= 0) { | ||||
|         toc.children[h2].children.push({ | ||||
|           title: `Scene break ${scenebreak}`, | ||||
|           slug: slugify(`scene-break-${scenebreakIndex}`), | ||||
|           children: [], | ||||
|         }); | ||||
|       } else { | ||||
|         toc.children.push({ | ||||
|           title: `Scene break ${scenebreak}`, | ||||
|           slug: slugify(`scene-break-${scenebreakIndex}`), | ||||
|           children: [], | ||||
|         }); | ||||
|       } | ||||
|     } | ||||
|   }); | ||||
|   return toc; | ||||
| } | ||||
| @ -12,12 +12,15 @@ export enum ContentPanelWidthSizes { | ||||
| export default function ContentPanel(props: ContentPanelProps): JSX.Element { | ||||
|   const width = props.width ? props.width : ContentPanelWidthSizes.default; | ||||
|   const widthCSS = | ||||
|     width === ContentPanelWidthSizes.default ? "max-w-[45rem]" : "w-full"; | ||||
|   const prose = props.autoformat ? "prose text-justify" : ""; | ||||
|     width === ContentPanelWidthSizes.default ? "max-w-2xl" : "w-full"; | ||||
| 
 | ||||
|   return ( | ||||
|     <div className={`grid pt-10 pb-20 px-6 desktop:py-20 desktop:px-10`}> | ||||
|       <main className={`${prose} ${widthCSS} place-self-center`}> | ||||
|       <main | ||||
|         className={`${ | ||||
|           props.autoformat && "formatted" | ||||
|         } ${widthCSS} place-self-center`}
 | ||||
|       > | ||||
|         {props.children} | ||||
|       </main> | ||||
|     </div> | ||||
|  | ||||
| @ -24,6 +24,10 @@ | ||||
|     @apply bg-dark text-light; | ||||
|   } | ||||
| 
 | ||||
|   mark { | ||||
|     @apply bg-mid px-2 | ||||
|   } | ||||
| 
 | ||||
|   /* SCROLLBARS STYLING */ | ||||
| 
 | ||||
|   * { | ||||
| @ -42,45 +46,82 @@ | ||||
|     @apply bg-dark rounded-full border-[3px] border-solid border-light; | ||||
|   } | ||||
| 
 | ||||
|   /* CHANGE PROSE DEFAULTS */ | ||||
|   /* CHANGE FORMATTED DEFAULTS */ | ||||
| 
 | ||||
|   .prose, | ||||
|   .prose p, | ||||
|   .prose h1, | ||||
|   .prose h2, | ||||
|   .prose h3, | ||||
|   .prose h4, | ||||
|   .prose h5, | ||||
|   .prose h6, | ||||
|   .prose a, | ||||
|   .prose strong { | ||||
|     @apply text-black; | ||||
|   .formatted h1, | ||||
|   .formatted h2, | ||||
|   .formatted h3, | ||||
|   .formatted h4, | ||||
|   .formatted h5, | ||||
|   .formatted h6 { | ||||
|     @apply text-center; | ||||
|   } | ||||
| 
 | ||||
|   .prose a { | ||||
|     @apply transition-colors underline-offset-2 decoration-dotted underline decoration-dark hover:text-dark; | ||||
|   .formatted h1 { | ||||
|     @apply text-4xl my-16; | ||||
|   } | ||||
| 
 | ||||
|   .prose footer { | ||||
|   .formatted h1 + h2 { | ||||
|     @apply -mt-10; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h2 { | ||||
|     @apply text-3xl my-12; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h2 + h3 { | ||||
|     @apply -mt-8; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h3 { | ||||
|     @apply text-2xl my-8; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h3 + h4 { | ||||
|     @apply -mt-6; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h4 { | ||||
|     @apply text-xl my-6; | ||||
|   } | ||||
| 
 | ||||
|   .formatted h5 { | ||||
|     @apply text-lg my-4; | ||||
|   } | ||||
| 
 | ||||
|   .formatted p, | ||||
|   .formatted strong { | ||||
|     @apply my-2 text-justify; | ||||
|   } | ||||
| 
 | ||||
|   .formatted footer { | ||||
|     @apply border-t-[3px] border-dotted pt-6; | ||||
|   } | ||||
| 
 | ||||
|   .prose footer > div { | ||||
|   .formatted footer > div { | ||||
|     @apply my-2 px-6 py-4 rounded-xl; | ||||
|   } | ||||
| 
 | ||||
|   .prose footer > div:target { | ||||
|   .formatted footer > div:target { | ||||
|     @apply bg-mid shadow-inner-sm shadow-shade; | ||||
|   } | ||||
| 
 | ||||
|   .prose li::marker { | ||||
|   .formatted li::marker { | ||||
|     @apply text-dark; | ||||
|   } | ||||
| 
 | ||||
|   .prose blockquote { | ||||
|   .formatted blockquote { | ||||
|     @apply border-l-dark; | ||||
|   } | ||||
| 
 | ||||
|   .formatted ul { | ||||
|     @apply list-disc pl-4; | ||||
|   } | ||||
| 
 | ||||
|   .formatted ol { | ||||
|     @apply list-decimal pl-4; | ||||
|   } | ||||
| 
 | ||||
|   /* INPUT */ | ||||
| 
 | ||||
|   input { | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 DrMint
						DrMint