📷
ZennのメディアキットにロゴだけのSVGが追加されたので Material UI で IconButton にする
Zenn のメディアキットに ロゴのアイコン部分SVGが追加されましたね。
この部分です👇
何が嬉しいかという話なのですが、たとえば自分のブログでZennへのリンクを貼るとき、Twitter や GitHub のアイコンと並べて表示したいときがあります。こういうやつです。
export default function App() {
return (
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
+ <Grid container justify="center" alignItems="center">
+ <Grid item xs={1}>
+ <IconButton target="_blank" href="https://twitter.com/">
+ <Twitter />
+ </IconButton>
+ </Grid>
+ <Grid item xs={1}>
+ <IconButton target="_blank" href="https://github.com/">
+ <GitHub />
+ </IconButton>
+ </Grid>
+ </Grid>
+ </div>
);
}
結果👇
ここに Zenn のアイコンも追加したいときは、以下のような手順を踏みます。
- Zenn の SVGファイル を import できるようにする
- React の場合:
import { ReactComponent as Logo } from './logo-only.svg';
- Next.js の場合:
next.config.js
にreact-svg-loader
の設定を追加して import できるようにします
- React の場合:
- import した SVG を、Material-UI の
<SvgIcon></SvgIcon>
で囲む - それっぽい表示になる
Zenn の SVGファイル を import できるようにする
React と Next.js でやりかたがすこし違いますが、共通しているのは public
ではなく src
ファイルとして扱いますので、以下のように配置します。
React の場合
+import { ReactComponent as Zenn } from "./logo-only.svg";
export default function App() {
return (
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
<Container maxWidth="sm">
<Grid container justify="center" alignItems="center">
<Grid item xs={1}>
<IconButton target="_blank" href="https://twitter.com/">
<Twitter />
</IconButton>
</Grid>
<Grid item xs={1}>
<IconButton target="_blank" href="https://github.com/">
<GitHub />
</IconButton>
</Grid>
</Grid>
</Container>
</div>
);
}
React の場合はシンプルで、上記のような import 文を書けばSVGコンポーネントとして扱えます。
Next.js の場合
next.config.js
に設定を追加することで、React と同じように import できるようになります。
こちらが参考になると思います。importできるようになったら、あとは先述した方法と同じです。
<SvgIcon></SvgIcon>
で囲む
import した SVG を、Material-UI の ではZennアイコンを表示していきましょう。Reactのケースで書いています。
+import { ReactComponent as Zenn } from "./logo-only.svg"; // React
export default function App() {
return (
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
<Container maxWidth="sm">
<Grid container justify="center" alignItems="center">
<Grid item xs={1}>
<IconButton target="_blank" href="https://twitter.com/">
<Twitter />
</IconButton>
</Grid>
<Grid item xs={1}>
<IconButton target="_blank" href="https://github.com/">
<GitHub />
</IconButton>
</Grid>
+ <Grid item xs={1}>
+ <IconButton target="_blank" href="https://zenn.dev/waddy">
+ <SvgIcon>
+ <Zenn />
+ </SvgIcon>
+ </IconButton>
+ </Grid>
+ </Grid>
</Container>
</div>
);
}
Material-UI の <SvgIcon>
で囲っているのがポイントです。結果は以下のようになります。
色なのですが、このあたりを見ていろいろ試したものの、うまく反映されませんでした。gタグにfillがあるとCSSでは変更できないみたいですね。
後述していますが、 gタグのfillをcurrentColor
にするとうまくいきました、catnoseさんありがとうございました。
今回は、SVG自体の色を変更しました。他になにかいい方法があったら教えて下さい🙇♂️
./logo-only.svg
<svg>
- <g fill="#3EA8FF">
+ <g fill="currentColor">
<path .../>
<path .../>
</g>
</svg>
これでいい感じに並べることができました。
おわりに
試したコードは codesandbox に置いています。
Discussion
svgを
img
タグではなくインラインで埋め込む場合、fill="currentColor"
とすることで外側からCSSで色を指定できるようになります。具体的には
というsvgをReactで以下のように読み込む場合、
CSSで
とすれば、SVGの
fill="currentColor"
に該当する部分が赤になります。おお、知りませんでした!たしかに、
fill="currentColor"
とすることで Material-UI 側のカラーが反映されるようになりました。この修正を入れるよう記事も直しておきます、ありがとうございます!