Skip to content

Add Tooling deployed On Scroll #258

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 7 commits into from
Jul 16, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,24 @@ npm install && npm run dev
- All articles are markdown and stored in `/src/content/docs/`.
- Navigation is JSON in `/src/config/sidebar.ts`

## Tooling on Scroll

If you'd like to add an entry to our [tooling list](http://docs.scroll.xyz/en/developers/scroll-contracts), create a PR to add a new `mdx` file in the [tooling content folder](src/content/tools), using the following template. You can also refer to other existing entries for reference.

```
---
name: "Safe"
category: ["Identity", "Wallet"]
excerpt: "Safe allows you to create smart wallet on chain."
logo: { src: "https://app.safe.global/images/safe-logo-green.png", alt: "Safe Logo" }
website: "https://app.safe.global"
network: ["Mainnet", "Testnet]
noAdditionalInfo: false
---

Add additional info here about how to access this tool on Scroll (ex. contract addresses, tutorials, API URLs)
```

## Credits

- Special thanks to the Chainlink team whose documentation we forked. Their repo is available [here](https://github.com/smartcontractkit/documentation) and viewable at [https://docs.chain.link/](https://docs.chain.link/).
1 change: 1 addition & 0 deletions public/locales/en/translation.json
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@
"erc1155TokenBridge": "ERC1155 Token Bridge",
"theScrollMessenger": "The Scroll Messenger",
"transactionFeesOnScroll": "Transaction Fees on Scroll",
"toolingDeployedOnScroll": "Tooling deployed On Scroll",
"l2Fee": "L2 Fee",
"l1Fee": "L1 Fee",
"gasOracle": "Gas Oracle",
Expand Down
164 changes: 164 additions & 0 deletions src/components/LinesEllipsis/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,164 @@
import { useState, useEffect, useRef } from "preact/hooks"

const agentStyle = {
position: "absolute",
bottom: 0,
left: 0,
height: 0,
overflow: "hidden",
paddingTop: 0,
paddingBottom: 0,
border: "none",
}

const mirrorProps = [
"box-sizing",
"width",
"font-size",
"font-weight",
"font-family",
"font-style",
"letter-spacing",
"text-indent",
"white-space",
"word-break",
"overflow-wrap",
"padding-left",
"padding-right",
]

function prevSibling(node, count) {
while (node && count--) {
node = node.previousElementSibling
}
return node
}

const LinesEllipsis = props => {
const { component: Component = "div", ellipsis, trimRight = true, basedOn, maxLine = 1, text, className, onReflow, ...rest } = props

const [displayedText, setDisplayedText] = useState(text)
const [clamped, setClamped] = useState(false)

const units = useRef([])
const shadowRef = useRef<HTMLElement>()
const targetRef = useRef()
const ellipsisRef = useRef()

useEffect(() => {
const handleSizeChanged = entries => {
if (targetRef.current) {
copyStyleToShadow()
reflow({ basedOn, text, maxLine })
}
}
const resizeObserver = new ResizeObserver(handleSizeChanged)
resizeObserver.observe(targetRef.current)

return () => {
if (targetRef.current) {
resizeObserver && resizeObserver.unobserve(targetRef.current)
}
}
}, [basedOn, text, maxLine])

const copyStyleToShadow = () => {
const targetStyle = window.getComputedStyle(targetRef.current)
mirrorProps.forEach(key => {
shadowRef.current.style[key] = targetStyle[key]
})
}

const reflow = props => {
/* eslint-disable no-control-regex */
const basedOn = props.basedOn || (/^[\x00-\x7F]+$/.test(props.text) ? "words" : "letters")

if (basedOn === "words") {
units.current = props.text.split(/\b|(?=\W)/)
} else if (basedOn === "letters") {
units.current = Array.from(props.text)
} else {
// default
units.current = props.text.split(/\b|(?=\W)/)
}
shadowRef.current.innerHTML = units.current
.map(c => {
return `<span class='LinesEllipsis-unit'>${c}</span>`
})
.join("")
const ellipsisIndex = putEllipsis(calcIndexes())
const nextClamped = ellipsisIndex > -1
const nextDisplayedText = nextClamped ? units.current.slice(0, ellipsisIndex).join("") : props.text
setClamped(nextClamped)
setDisplayedText(nextDisplayedText)
onReflow({ clamped: nextClamped, text: nextDisplayedText })
}

// return the index of the first letter/word of each line
// row count: maxLine + 1
const calcIndexes = () => {
const indexes = [0]
let spanNode = shadowRef.current.firstElementChild
if (!spanNode) return indexes

let index = 0
let line = 1
let offsetTop = spanNode.offsetTop
while ((spanNode = spanNode.nextElementSibling)) {
if (spanNode.offsetTop > offsetTop) {
line++
indexes.push(index)
offsetTop = spanNode.offsetTop
}
index++
if (line > maxLine) {
break
}
}
return indexes
}

const putEllipsis = indexes => {
// no ellipsis
if (indexes.length <= maxLine) return -1
const lastIndex = indexes[maxLine]
const truncatedUnits = units.current.slice(0, lastIndex)

// the first letter/word of maxLine + 1 row
const maxOffsetTop = shadowRef.current.children[lastIndex].offsetTop
shadowRef.current.innerHTML =
truncatedUnits
.map((c, i) => {
return `<span class='LinesEllipsis-unit'>${c}</span>`
})
.join("") + `<span class='LinesEllipsis-ellipsis'>${ellipsisRef.current.innerHTML}</span>`
const ellipsisNode = shadowRef.current.lastElementChild
let lastTextNode = prevSibling(ellipsisNode, 1)
while (
lastTextNode &&
(ellipsisNode.offsetTop > maxOffsetTop ||
ellipsisNode.offsetHeight > lastTextNode.offsetHeight ||
ellipsisNode.offsetTop > lastTextNode.offsetTop)
) {
shadowRef.current.removeChild(lastTextNode)
lastTextNode = prevSibling(ellipsisNode, 1)
truncatedUnits.pop()
}
return truncatedUnits.length
}

return (
<>
<Component className={`LinesEllipsis ${clamped ? "LinesEllipsis--clamped" : ""} ${className}`} ref={targetRef} {...rest}>
{trimRight ? displayedText.trimRight() : displayedText}
{clamped && <span className="LinesEllipsis-ellipsis">{ellipsis}</span>}
</Component>
<div style={agentStyle} ref={shadowRef} className={`LinesEllipsis-shadow ${className}`}></div>
<span style={agentStyle} ref={ellipsisRef}>
{ellipsis}
</span>
</>
)
}

export default LinesEllipsis
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
.additionalInfo {
height: 100%;
overflow: auto;
background: rgba(255, 255, 255, 0.5);
border-radius: 15px;
display: flex;
justify-content: center;
max-width: 532px;
margin: 0 auto;
position: relative;
}
.closeButton {
position: absolute;
right: 20px;
top: 20px;
cursor: pointer;
display: none;
}
.infoBox {
padding: 18px 20px;
width: 100%;
}

.infoBox p {
font-size: 14px;
}

.title {
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: normal;
letter-spacing: 0.18px;
margin-bottom: 15px;
}

.content {
max-height: 460px;
overflow: auto;
}

.noToolInfo {
text-align: center;
margin: 0 auto;
height: max-content;
max-width: 280px;
align-self: center;
}

.noToolInfo svg {
margin-bottom: 20px;
}

.noToolInfoTitle {
color: #ababab;
text-align: center;
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: normal;
letter-spacing: 0.18px;
margin-bottom: 8px;
}

.noToolInfoDescription {
color: #ababab;
text-align: center;
font-size: 14px;
font-style: normal;
font-weight: 400;
line-height: 18px; /* 128.571% */
letter-spacing: 0.14px;
}

@media screen and (max-width: 1300px) {
.closeButton {
display: block;
}
.additionalContainer {
position: fixed;
top: 0;
right: 0;
bottom: 0;
left: 0;
background: rgba(16, 16, 16, 0.2);
z-index: 9999;
height: 100%;
max-height: 100%;
padding: 20px;
display: flex;
}
.additionalInfo {
background: #ffffff;
border-radius: 15px;
justify-self: center;
align-self: center;
width: 100%;
height: 532px;
}

.noToolSelected {
display: none;
}
.noToolInfo {
padding-top: 20px;
}
}
Loading