このテーマのゴール
ここでやりたいのは、「金額」と「税率」を props で受け取り、コンポーネントの中で計算して「税込み価格」を表示することです。
つまり、「見た目+計算ロジック」をひとつの部品としてまとめる練習です。
ポイントは 3 つです。
金額・税率を props で受け取る
コンポーネントの中で税込み価格を計算する
計算結果をきれいな形で表示する
これができると、「ちょっとしたビジネスロジックをコンポーネントに閉じ込める」感覚がつかめます。
まずは完成イメージのコードを見る
シンプルな税込み価格コンポーネント
// components/TaxPrice.tsx
type TaxPriceProps = {
amount: number; // 税抜き金額
taxRate: number; // 税率(例:0.1 = 10%)
};
export function TaxPrice({ amount, taxRate }: TaxPriceProps) {
const taxIncluded = Math.round(amount * (1 + taxRate));
return (
<p>
税抜き {amount.toLocaleString()} 円 → 税込み{" "}
<strong>{taxIncluded.toLocaleString()} 円</strong>
</p>
);
}
TSX// app/page.tsx
import { TaxPrice } from "./components/TaxPrice";
export default function Page() {
return (
<main style={{ padding: "24px", fontFamily: "system-ui, sans-serif" }}>
<h1 style={{ fontSize: "22px", marginBottom: "16px" }}>
税込み価格コンポーネントの例
</h1>
<TaxPrice amount={1000} taxRate={0.1} />
<TaxPrice amount={2980} taxRate={0.1} />
<TaxPrice amount={500} taxRate={0.08} />
</main>
);
}
TSX画面には、例えばこんな感じで表示されます。
税抜き 1,000 円 → 税込み 1,100 円
税抜き 2,980 円 → 税込み 3,278 円
税抜き 500 円 → 税込み 540 円
同じ TaxPrice コンポーネントを使い回しつつ、金額と税率だけを変えているのがポイントです。
props で「金額」と「税率」を受け取る
型定義で「何を受け取るコンポーネントか」をはっきりさせる
まずはこの部分から。
type TaxPriceProps = {
amount: number; // 税抜き金額
taxRate: number; // 税率(例:0.1 = 10%)
};
TSXここでやっているのは、
このコンポーネントはamount(税抜き金額)と taxRate(税率)という 2 つの数値を受け取ります
という“約束”を TypeScript で書いている、ということです。
これがあることで、
<TaxPrice amount="1000" taxRate={0.1} /> のように文字列を渡すとエラー<TaxPrice amount={1000} /> のように taxRate を渡し忘れてもエラー
といった具合に、「間違った使い方」をコンパイル時に止めてくれます。
関数の引数で props を受け取る
次に、この部分。
export function TaxPrice({ amount, taxRate }: TaxPriceProps) {
...
}
TSXこれは、
TaxPriceはTaxPriceProps型のオブジェクトを受け取る- そのオブジェクトから
amountとtaxRateを取り出して使う
という意味です。
イメージとしては、こう呼ばれている感じです。
TaxPrice({ amount: 1000, taxRate: 0.1 });
TaxPrice({ amount: 2980, taxRate: 0.1 });
TaxPrice({ amount: 500, taxRate: 0.08 });
TSXJSX では <TaxPrice amount={1000} taxRate={0.1} /> と書きますが、
中身では「{ amount: 1000, taxRate: 0.1 } というオブジェクト」が渡されている、と考えると分かりやすいです。
税込み価格の計算ロジックをコンポーネントに閉じ込める
計算式をちゃんと理解する
税込み価格の計算はシンプルです。
税込み価格 = 税抜き金額 × (1 + 税率)
例えば、税抜き 1,000 円・税率 10% の場合は、
1,000 × (1 + 0.1) = 1,000 × 1.1 = 1,100
これをそのままコードにすると、こうなります。
const taxIncluded = Math.round(amount * (1 + taxRate));
TSXここで Math.round を使っているのは、小数点を四捨五入して整数にするためです。
金額はふつう「1円単位」で扱うので、2980 * 1.1 = 3278.0000000004 のような微妙な誤差をきれいに丸めてあげています。
表示を少しだけ“人間向け”にする
そのまま数字を表示してもいいのですが、toLocaleString() を使うと「3,278」のようにカンマ区切りにできます。
<p>
税抜き {amount.toLocaleString()} 円 → 税込み{" "}
<strong>{taxIncluded.toLocaleString()} 円</strong>
</p>
TSXここでやっていることは、
税抜き金額も税込み金額も、toLocaleString() で見やすくしている
税込み金額は <strong> で少し強調している
という、ちょっとした UX の工夫です。
こういう「小さな気配り」をコンポーネントの中に閉じ込めておくと、
どこで使っても同じクオリティで表示されるようになります。
親コンポーネントから「金額」と「税率」を変えて使い回す
使う側は「値を渡すだけ」で済む
page.tsx 側のコードをもう一度見てみます。
<TaxPrice amount={1000} taxRate={0.1} />
<TaxPrice amount={2980} taxRate={0.1} />
<TaxPrice amount={500} taxRate={0.08} />
TSXやっていることはとてもシンプルで、
1つ目の行では「税抜き 1,000 円・税率 10%」
2つ目の行では「税抜き 2,980 円・税率 10%」
3つ目の行では「税抜き 500 円・税率 8%」
という“条件”だけを渡しているだけです。
計算式や表示の仕方は、全部 TaxPrice コンポーネントの中に隠れている。
使う側は「金額と税率を渡せば、いい感じに税込み価格を出してくれる部品」として扱える。
これが「ロジックをコンポーネントに閉じ込める」ことの強さです。
まとめ:このコンポーネントからつかんでほしいこと
この「金額と税率を受け取って税込み価格を出すコンポーネント」で、つかんでほしいのは次の感覚です。
コンポーネントは「見た目」だけでなく「計算ロジック」も一緒に持てる
変わるのは「入力値(amount, taxRate)」で、計算式と表示は毎回同じ
props に型をつけることで、「このコンポーネントは何を受け取るのか」がはっきりする
ここが腑に落ちると、
割引後価格を出すコンポーネント
送料込みの合計金額を出すコンポーネント
ポイント還元額を計算して表示するコンポーネント
みたいな「ちょっとしたビジネス計算」を、どんどん部品として切り出せるようになります。
もしよければ、この TaxPrice を少しアレンジしてみてください。
例えば「税額(いくら税金が乗ったか)」も一緒に表示するようにすると、taxAmount = taxIncluded - amount みたいな“派生値”をどう扱うか、さらに感覚が深まります。

