/n 改行&単語置換ツール

テキストの中の特定の言葉を一括で置き換えたり、 句読点に沿って改行を自動で行うツールです。
AIで処理しきれない固有名詞などの一括変更や、 文章の整形にお役立てください。

置換対象テキスト

0文字

置換リスト(1行: 置換前,置換後)

0文字

置換結果

ここに結果が表示されます
copy

まだコピーされていません

詳細設定

<div class="text-tool">
<style>
/* -----------------------------
   基本レイアウト
----------------------------- */
.flex {
  display: flex; /* 横並び配置 */
  gap: 20px; /* 要素間の隙間 */
  justify-content: flex-start; /* 左寄せ配置 */
  flex-wrap: nowrap; /* 折り返さない */
}
.input-section {
  display: flex; /* 縦方向のレイアウトを設定 */
  flex-direction: column; /* 子要素を縦並びに */
  gap: 13px; /* 子要素の間隔 */
  flex: 1; /* 横幅を均等に広げる */
  min-width: 300px; /* 最小幅を確保 */
  position: relative; /* 子要素の絶対位置指定に備える */
}
.input-section label {
  font-size: 16px; /* ラベルの文字サイズ */
  font-weight: 500; /* 少し太め */
  margin-bottom: 4px; /* 下の余白 */
  display: flex; /* フレックスレイアウト */
  justify-content: space-between; /* 両端揃え */
  align-items: center; /* 垂直中央揃え */
}

/* -----------------------------
   小見出し(番号付き)
----------------------------- */
.heading-24 {
  position: relative; /* 番号の配置用 */
  padding-top: 0.5em; /* 上余白を確保 */
  margin: 30px 0 10px; /* 外側の余白 */
  color: #333; /* 文字色 */
  font-size: 20px; /* フォントサイズ */
  font-weight: 600; /* 太字 */
}

.heading-24::before {
  position: absolute; /* 番号を絶対配置 */
  bottom: 0; /* 下基準 */
  left: 0; /* 左揃え */
  z-index: -1; /* テキストの背面に配置 */
  font-size: 3em; /* 大きな番号サイズ */
  line-height: 1; /* 行の高さ調整 */
  pointer-events: none; /* 番号にクリック反応なし */
  opacity: 0.9; /* 薄く表示 */
  content: attr(data-number); /* data-number属性の数字を表示 */
}

.heading-24.gray::before {
  color: #ddd; /* 灰色の番号 */
}
.heading-24.pink::before {
  color: #ffd6dc; /* ピンクの番号 */
}

/* -----------------------------
   テキストエリア
----------------------------- */
textarea {
  width: 100%; /* 横幅いっぱい */
  height: 180px; /* 高さ固定 */
  padding: 10px; /* 内側余白 */
  border: 0px solid #ddd; /* 枠線なし */
  border-radius: 6px; /* 角丸 */
  font-size: 16px; /* 文字サイズ */
  font-family: sans-serif; /* フォント */
  box-sizing: border-box; /* paddingを含めてサイズ計算 */
  background: rgba(255,255,255,0.85); /* 半透明の白背景 */
  box-shadow: 0 2px 6px rgba(0,0,1,0.1); /* ふんわり影 */
  resize: none; /* サイズ変更を禁止 */
}
/* 共通:テキストエリアと結果枠のスクロールを装飾 */
textarea::-webkit-scrollbar,
#texttool-output::-webkit-scrollbar {
  width: 12px; /* スクロールバーの太さ */
}

/* 背景(トラック部分) */
textarea::-webkit-scrollbar-track,
#texttool-output::-webkit-scrollbar-track {
  background-color: #f1f3f9; /* やさしいグレー */
  border-radius: 10px;
}

/* スクロールつまみ(サム部分) */
textarea::-webkit-scrollbar-thumb,
#texttool-output::-webkit-scrollbar-thumb {
  background-color: #c0c8d8; /* 淡いグレー寄りの青 */
  border-radius: 10px;       /* ← 角丸ここで効く! */
}

/* hover時の色変化(ふわっと濃く) */
textarea::-webkit-scrollbar-thumb:hover,
#texttool-output::-webkit-scrollbar-thumb:hover {
  background-color: #a5b3c9;
}

.char-count {
  position: absolute; /* テキストエリア内右下に固定 */
  bottom: 5px;
  right: 10px;
  font-size: 10px; /* 小さめの文字サイズ */
  color: #BBBCBF; /* 薄いグレー文字 */
  pointer-events: none; /* クリック操作を無効にする */
}

/* -----------------------------
   出力エリア
----------------------------- */
#texttool-output {
  width: 100%; /* 横幅いっぱい */
  height: calc(2 * 180px + 13px); /* 入力2つ分の高さ+隙間 */
  padding: 13px; /* 内側余白 */
  border: 0px solid #ddd; /* 枠線 */
  border-radius: 6px; /* 角丸 */
  box-shadow: 0 2px 6px rgba(0,0,1,0.1); /* 軽い影 */
  background: rgba(225, 235, 245, 0.85); /* 薄いグレー寄りの青背景 */
  white-space: pre-wrap; /* 改行を保持して折り返し */
  word-wrap: break-word; /* 長い単語を折り返す */
  font-size: 16px;
  line-height: 1.5;
  font-family: sans-serif;
  overflow-y: auto; /* スクロール可能 */
}

/* -----------------------------
   ボタン
----------------------------- */
button {
  padding: 8px 12px; /* 内側余白 */
  border-radius: 6px; /* 角丸 */
  border: none; /* 枠線なし */
  background-color: #4CAF50; /* 緑色ボタン */
  color: white; /* 白文字 */
  cursor: pointer; /* ポインター表示 */
  font-size: 16px; /* 文字サイズ */
}
button.secondary {
  background-color: #777; /* サブボタンはグレー */
}

/* -----------------------------
   ラジオボタン
----------------------------- */
.radio-1 {
  display: flex; /* 横並び */
  flex-wrap: wrap; /* 折り返し可 */
  gap: .3em 2em; /* 行間と列間の間隔 */
  border: none; /* 枠線なし */
}
.radio-1 label {
  display: flex; /* 横並び */
  align-items: center; /* 縦中央揃え */
  gap: 0 .5em; /* テキストと丸の間隔 */
  position: relative;
  cursor: pointer;
}
.radio-1 input { display: none; } /* デフォルトのラジオを非表示 */

.radio-1 label::before,
.radio-1 label:has(:checked)::after {
  border-radius: 50%; /* 丸型 */
  content: ''; /* 空要素 */
}
.radio-1 label::before {
  width: 18px;
  height: 18px;
  background-color: #e6edf3; /* 未選択時の背景 */
}
.radio-1 label:has(:checked)::after {
  position: absolute;
  top: 50%;
  left: 9px;
  transform: translate(-50%, -50%);
  width: 10px;
  height: 10px;
  background-color: #595959; /* 選択時の内側色 */
  animation: anim-radio-1 .3s linear; /* 選択時のアニメーション */
}
@keyframes anim-radio-1 {
  0% { box-shadow: 0 0 0 1px transparent; }
  50% { box-shadow: 0 0 0 10px #59595933; }
  100% { box-shadow: 0 0 0 10px transparent; }
}

/* -----------------------------
   チェックボックス
----------------------------- */
.checkbox-1 {
  display: flex;
  flex-wrap: wrap;
  gap: .5em 2em;
  border: none;
}
.checkbox-1 label {
  display: flex;
  align-items: center;
  gap: 0 .5em;
  position: relative;
  cursor: pointer;
}
.checkbox-1 input { display: none; } /* 標準チェックを非表示 */
.checkbox-1 label::before,
.checkbox-1 label:has(:checked)::after {
  content: '';
}
.checkbox-1 label::before {
  width: 17px;
  height: 17px;
  border-radius: 3px;
  background-color: #e6edf3; /* チェック前の背景 */
}
.checkbox-1 label:has(:checked)::before {
  background-color: #595959; /* チェック後の背景色 */
}
.checkbox-1 label:has(:checked)::after {
  position: absolute;
  top: 6px;
  left: 6px;
  transform: rotate(45deg); /* ✓ の角度 */
  width: 4px;
  height: 8px;
  border: solid #fff;
  border-width: 0 2px 2px 0; /* ✓ を描く線 */
}
.checkbox-1 label:has(:checked)::before {
  background-color: #595959;
  animation: anim-checkbox-1 .3s linear;
}
@keyframes anim-checkbox-1 {
  0% { box-shadow: 0 0 0 1px transparent; }
  50% { box-shadow: 0 0 0 10px #59595933; }
  100% { box-shadow: 0 0 0 10px transparent; }
}

/* -----------------------------
   レスポンシブ
----------------------------- */
@media (max-width: 1400px) {
  .flex {
    flex-direction: column; /* 狭い画面では縦並び */
    gap: 20px; /* 間隔を広めに */
  }
}

/* -----------------------------
   コピーとバツアイコン
----------------------------- */
.img-clear {
  display: block;
  margin-left: auto; /* 右寄せ配置 */
  width: 24px; /* アイコンサイズ */
  height: 24px;
  cursor: pointer; /* クリックできる */
  opacity: 0.7; /* 少し透過 */
  transition: opacity 0.2s ease; /* フェード効果 */
}
.img-clear:hover {
  opacity: 1; /* ホバーで明るく */
}

.img-copy {
  width: 32px; /* コピーアイコンを少し大きめに */
  height: 32px;
  cursor: pointer;
  opacity: 0.85;
  transition: opacity 0.2s;
}
.img-copy:hover {
  opacity: 1;
  transform: scale(1.05); /* ホバー時にふわっと拡大 */
}

/* -----------------------------
   h2目次強制非表示
----------------------------- */
#toc, .toc {
  display: none !important; /* WordPressなどの自動目次を強制的に非表示 */
}
lay: flex;
  align-items: center;
  gap: 0 .5em;
  position: relative;
  cursor: pointer;
}
.radio-1 input { display: none; }
.radio-1 label::before,
.radio-1 label:has(:checked)::after {
  border-radius: 50%;
  content: '';
}
.radio-1 label::before {
  width: 18px;
  height: 18px;
  background-color: #e6edf3;
}
.radio-1 label:has(:checked)::after {
  position: absolute;
  top: 50%;
  left: 9px;
  transform: translate(-50%, -50%);
  width: 10px;
  height: 10px;
  background-color: #595959;
  animation: anim-radio-1 .3s linear;
}
@keyframes anim-radio-1 {
  0% { box-shadow: 0 0 0 1px transparent; }
  50% { box-shadow: 0 0 0 10px #59595933; }
  100% { box-shadow: 0 0 0 10px transparent; }
}

/* -----------------------------
   チェックボックス
----------------------------- */
.checkbox-1 {
  display: flex;
  flex-wrap: wrap;
  gap: .5em 2em;
  border: none;
}
.checkbox-1 label {
  display: flex;
  align-items: center;
  gap: 0 .5em;
  position: relative;
  cursor: pointer;
}
.checkbox-1 input { display: none; }
.checkbox-1 label::before,
.checkbox-1 label:has(:checked)::after {
  content: '';
}
.checkbox-1 label::before {
  width: 17px;
  height: 17px;
  border-radius: 3px;
  background-color: #e6edf3;
}
.checkbox-1 label:has(:checked)::before {
  background-color: #595959;
}
.checkbox-1 label:has(:checked)::after {
  position: absolute;
  top: 6px;
  left: 6px;
  transform: rotate(45deg);
  width: 4px;
  height: 8px;
  border: solid #fff;
  border-width: 0 2px 2px 0;
}
.checkbox-1 label:has(:checked)::before {
  background-color: #595959;
  animation: anim-checkbox-1 .3s linear;
}

@keyframes anim-checkbox-1 {
  0% { box-shadow: 0 0 0 1px transparent; }
  50% { box-shadow: 0 0 0 10px #59595933; }
  100% { box-shadow: 0 0 0 10px transparent; }
}



/* -----------------------------
   レスポンシブ
----------------------------- */
@media (max-width: 1400px) {
  .flex {
    flex-direction: column;
    gap: 20px;
  }
}


/* -----------------------------
   コピーとバツアイコン
----------------------------- */
.img-clear {
  display: block;
  margin-left: auto;
  width: 24px;
  height: 24px;
  cursor: pointer;
  opacity: 0.7;
  transition: opacity 0.2s ease;
}
.img-clear:hover {
  opacity: 1;
}


.img-copy {
  width: 32px;
  height: 32px;
  cursor: pointer;
  opacity: 0.85;
  transition: opacity 0.2s;
}
.img-copy:hover {
  opacity: 1;
  transform: scale(1.05); /* ← ふわっと拡大 */
}



/* -----------------------------
   h2目次強制非表示
----------------------------- */
#toc, .toc {
  display: none !important;
}



  </style>







 <div class="flex">
<!-- =========================================
     01 置換テキスト
     ========================================= -->
  <div class="input-section">
    <h2 class="heading-24 gray" data-number="01">置換対象テキスト</h2>
    <label><span class="dli-close" id="clearInput1"></span></label>
    <textarea id="texttool-inputText">吾輩は、猫である!名前は、まだ無い。
どこで 生れたか、とんと 見当がつかぬ。</textarea>
    <div class="char-count" id="countInput1">0文字</div>
<!-- 01〜03入力エリアの中のバツボタン -->
<label>
  <img src="http://tkv-tools.com/wp-content/uploads/2025/10/icons8-ウィンドウを閉じる-48.png"
       alt="clear"
       class="img-clear"
       data-target="texttool-inputText">
</label>


<!-- =========================================
     02 置換リスト
     ========================================= -->

    <h2 class="heading-24 gray" data-number="02">置換リスト(1行: 置換前,置換後)</h2>
    <label><span class="dli-close" id="clearInput2"></span></label>
    <textarea id="texttool-replaceList">吾輩,ワガハイ
名前,ネーム</textarea>
    <div class="char-count" id="countInput2">0文字</div>
<label>
  <img src="http://tkv-tools.com/wp-content/uploads/2025/10/icons8-ウィンドウを閉じる-48.png"
       alt="clear"
       class="img-clear"
       data-target="texttool-replaceList">
</label>

<!-- =========================================
     03 詳細設定
     ========================================= -->

    <h2 class="heading-24 gray" data-number="03">詳細設定</h2>
    <div>
      <label>半角スペース処理</label>
      <fieldset class="radio-1">
        <label><input type="radio" name="texttool-spaceOption" value="remove">削除</label>
        <label><input type="radio" name="texttool-spaceOption" value="comma" checked>半角スペース→読点「、」</label>
      </fieldset>
    </div>

    <div>
      <label>改行・整形オプション</label>
      <fieldset class="checkbox-1">
        <label><input type="checkbox" id="texttool-breakComma" checked>「、」で改行</label>
        <label><input type="checkbox" id="texttool-breakPeriod" checked>「。」で改行</label>
        <label><input type="checkbox" id="texttool-breakExMark" checked>「!」「?」「!」で改行</label>
        <label><input type="checkbox" id="texttool-removeEmptyLines" checked>空白行を消す</label>
        <label><input type="checkbox" id="texttool-keepPunctuation">句読点を残す</label>
      </fieldset>
    </div>



<!-- =========================================
     置換ボタン
     ========================================= -->
    <div style="display:flex; gap:8px;">
      <button id="texttool-runBtn">置換する</button>
      <button class="secondary" id="texttool-clearBtn">消す</button>
    </div>
  </div>



<!-- =========================================
     04 置換結果
     ========================================= -->
<div class="input-section">
  <h2 class="heading-24 pink" data-number="04">置換結果</h2>

  <div id="texttool-output">ここに結果が表示されます</div>

  <div class="copy-area">
    <img src="http://tkv-tools.com/wp-content/uploads/2025/10/icons8-コピー-48.png"
         alt="copy"
         class="img-copy"
         id="texttool-copyBtn">
    <p id="texttool-copyStatus">まだコピーされていません</p>
  </div>
</div>

</div>


<!-- =========================================
     JS
========================================= -->

  <script>
    (function(){
      const url = "https://script.google.com/macros/s/AKfycbzafu2KCoApAg2VaRKcjI4OVbsKjyKGpPKhHki0Y-edXTqDmDI6gwTy9QI-GfBSmgTwMg/exec"; // ← GAS Web API URL に差し替え

      const inputTextEl = document.getElementById('texttool-inputText');
      const replaceListEl = document.getElementById('texttool-replaceList');
      const outputEl = document.getElementById('texttool-output');
      const copyStatusEl = document.getElementById('texttool-copyStatus');

      document.getElementById('texttool-runBtn').addEventListener('click', async ()=>{
        const spaceOption = document.querySelector('input[name="texttool-spaceOption"]:checked').value;
        const options = {
          spaceOption,
          breakComma: document.getElementById('texttool-breakComma').checked,
          breakPeriod: document.getElementById('texttool-breakPeriod').checked,
          breakExMark: document.getElementById('texttool-breakExMark').checked,
          keepPunctuation: document.getElementById('texttool-keepPunctuation').checked,
          removeEmptyLines: document.getElementById('texttool-removeEmptyLines').checked
        };

        outputEl.textContent = "処理中…";

        try {
          const params = new URLSearchParams({
            inputText: inputTextEl.value,
            replaceList: replaceListEl.value,
            options: JSON.stringify(options)
          });
          const res = await fetch(url + "?" + params);
          const data = await res.json();
          if(data.result){
            outputEl.innerHTML = data.result; // HTMLタグを反映
            copyStatusEl.textContent = 'まだコピーされていません';
            copyStatusEl.style.color = '#555';
          } else {
            outputEl.textContent = "エラー: " + (data.error || "不明なエラー");
          }
        } catch(err){
          outputEl.textContent = "通信エラー: " + err.message;
        }
      });

      document.getElementById('texttool-clearBtn').addEventListener('click', ()=>{
        inputTextEl.value = '';
        replaceListEl.value = '';
      });

      document.getElementById('texttool-copyBtn').addEventListener('click', ()=>{
        const text = outputEl.innerText || '';
        if(!text) return;
        navigator.clipboard.writeText(text).then(()=>{
          copyStatusEl.textContent = 'コピーしました!';
          copyStatusEl.style.color = '#007bff';
          setTimeout(()=>{ copyStatusEl.textContent='まだコピーされていません'; copyStatusEl.style.color='#555'; },2000);
        }).catch(err=>{ console.error(err); });
      });
    })();
// --- バツボタンで入力欄をクリア ---
document.querySelectorAll('.img-clear').forEach(btn => {
  btn.addEventListener('click', () => {
    const targetId = btn.getAttribute('data-target');
    const targetEl = document.getElementById(targetId);
    if (targetEl) targetEl.value = '';
  });
});

// --- コピー機能 ---
document.getElementById('texttool-copyBtn').addEventListener('click', ()=>{
  const text = document.getElementById('texttool-output').innerText || '';
  if(!text) return;
  navigator.clipboard.writeText(text).then(()=>{
    const copyStatusEl = document.getElementById('texttool-copyStatus');
    copyStatusEl.textContent = 'コピーしました!';
    copyStatusEl.style.color = '#007bff';
    setTimeout(()=>{
      copyStatusEl.textContent = 'まだコピーされていません';
      copyStatusEl.style.color = '#555';
    },2000);
  });
});



  </script>
</div>