Option Explicit

'===========================================================
' 部品_転記_列単位 / TransferColumn_WithMap
'   ・マッピング表の各行に従い、転記元の「列」を、最終行まで（最終行は可変）、転記先の列へ転記する（列単位・値のみ）
'     → Transfers a whole column (from the start row down to its last row, which is variable) from the source
'        to the destination for each row of the mapping table (column by column, values only).
'
'   ・マッピング表の1行が、転記する1列分になる。複数列は、表に行を足すだけで増やせる
'     → One mapping row = one column to transfer; add rows to the table to transfer more columns.
'
'   ・マッピング表は、範囲設定_行可変 などで作った Range を渡す
'     表の中は、どの列に何が入っているかを、引数（列の位置）で指定する（表を自由にデザインできる）
'     → Pass the mapping table as a Range made by a range-setting component; which column holds what is
'        specified by arguments (column positions), so the table can be designed freely.
'
'   ・名前に「転記（Transfer）」が付く部品は、マッピング表を使う
'     → Components named "転記 (Transfer)" use a mapping table.
'       セル単位は「転記_セル単位」、列単位は「転記_列単位」の、別の部品である
'       → Cell-by-cell is "転記_セル単位", column-by-column is "転記_列単位"; they are separate.
'
'   ※ この部品は Sub（プロシージャ）ではなく「Function（関数）」で、成功／失敗を Boolean で返す
'     → ※ This component is a Function (not a Sub) that returns success/failure as a Boolean.
'===========================================================

'===========================================================
' ■区分 / Classification
'   ・基礎区分：応用 ／ 用途区分：処理 ／ 操作対象区分：範囲
'     → Base: application / Purpose: process / Target: range
'
' ■バージョン / Version
'   ・Version 1.0（2026-10-29）
'===========================================================

'===========================================================
' ■URL（WordPress部品ページ）
'   https://feelcodelab.com/vba_parts/transfercolumn_withmap/
'===========================================================

'===========================================================
' ■前提条件（AI誤動作防止の最重要項目） / Preconditions
'   ・【最重要】この部品は Function（関数）であり、戻り値（Boolean）を返す
'     → 転記できた場合は True、実行時にできなかった場合は False（この場合は、エラーでは止まらない）
'     → 呼び出し側は、必ず戻り値を確認してから後続処理を行い、メッセージも呼び出し側で表示する
'       （False のときは、MsgBox のあとに Exit Sub まで書く）
'     → [MOST IMPORTANT] This component is a Function that returns a Boolean: True if transferred, False if
'        it failed at run time (no error is raised then). The caller must check the return value before the
'        following processing and show any message itself (write Exit Sub after the MsgBox).
'
'   ・【最重要】転記元のブック（vSrcWb）と、転記先のブック（vDstWb）は、必ず引数で指定する（省略できない）
'     → ファイルを開く部品の後は、ActiveWorkbook が開いたファイルに切り替わる。
'       開いた直後に、ActiveWorkbook を変数へ控えて、その変数を渡す
'     → [MOST IMPORTANT] Always specify the source and destination workbooks (vSrcWb / vDstWb).
'        After the "open file" component runs, ActiveWorkbook switches to the opened file, so keep it in a
'        variable right after opening and pass that variable.
'
'   ・【最重要】マッピング表の範囲（vMapRng）は、見出し行を含めない、データの行だけの範囲を渡す
'     → 範囲は、範囲設定_行可変などで作る。最終行は、必ずデータが入っている列で判定する
'     → [MOST IMPORTANT] Pass only the data rows of the mapping table (without the header row).
'
'   ・【最重要】列の位置（vColSrcSheet 〜 vColDstCol）は、マッピング表の範囲の「左端の列」を 1 とした番号で指定する
'     → 例：範囲が A 列から始まる場合、B 列は 2。範囲が B 列から始まる場合、B 列は 1
'     → [MOST IMPORTANT] Column positions are numbers counted with the left-most column of the mapping
'        range as 1 (if the range starts at column A, column B is 2).
'
'   ・マッピング表の例（A 列から G 列。範囲は A 列から始まる）
'     → Mapping table example (columns A to G; the range starts at column A):
'
'        名称 | 転記元シート名 | 転記元開始行 | 転記元列位置 | 転記先シート名 | 転記先開始行 | 転記先列位置
'        内容 | 例1_転記元     | 2            | 2            | 例1_転記先     | 14           | 2
'        数量 | 例2_転記元     | 2            | 3            | 例2_転記先     | 14           | 10
'
'        この場合の列の位置は、転記元シート名＝2、転記元開始行＝3、転記元列位置＝4、
'        転記先シート名＝5、転記先開始行＝6、転記先列位置＝7 になる
'        → Here the positions are: source sheet = 2, source start row = 3, source column = 4,
'           destination sheet = 5, destination start row = 6, destination column = 7.
'
'   ・引数と表の並びは、他の部品と同じく「行 → 列」の順（開始行、列位置の順）にそろえる
'     → Arguments and the table follow the same "row, then column" order as the other components.
'
'   ・表の「列位置」「開始行」は、1 以上の数字で書く（"B" のようなアルファベットではなく、B 列なら 2）
'     → The column position and start row in the table are numbers of 1 or more (column B is 2, not "B").
'
'   ・転記する範囲は、転記元の「開始行」から、その列の「最終行」まで（最終行は、転記元の、その列で判定する）
'     → The transferred range runs from the source start row down to the last row of that source column.
'       その列に、開始行以降のデータが無い場合は、その行（列）は何もせず、次の行へ進む（エラーではない）
'       → If that column has no data at or below the start row, that mapping row is skipped (not an error).
'
'   ・シート名に "ActiveSheet" と書くと、その時点で、指定したブック（vSrcWb／vDstWb）の、
'     アクティブなシートを指す（テンプレートのシートをコピーした直後など、シート名が定まらないときに使う）
'     → 転記を始める前に、1 回だけシート名に置き換える
'     → Entering "ActiveSheet" as a sheet name refers to the active sheet of the specified workbook at that
'        moment; it is resolved to a sheet name once before transferring.
'
'   ・転記するのは「値のみ」（書式・数式は転記しない。数式は、結果の値になる）
'     → Only values are transferred (formatting and formulas are not; a formula becomes its result value).
'
'   ・転記を始める前に、マッピング表の全行を確認する
'     → 1行でも問題があれば、1列も転記せずに、行番号を示すエラーで止まる
'     → Before transferring, all rows of the mapping table are checked; if any row is wrong, nothing is
'        transferred and it stops with an error naming the row.
'
'   ・転記の途中で、実行時の失敗（保護されたシートなど）が起きた場合、それまでに転記した列は、元に戻らない
'     （False を返したあとも、書き込み済みの値は残る）
'     → If a run-time failure happens midway, what was already transferred is not rolled back.
'
'   ・設定の誤りは、False ではなく、原因を示すエラーで止まる（Err.Raise）
'       - 転記元ブック（vSrcWb）が Nothing（vbObjectError + 1001）
'       - 転記先ブック（vDstWb）が Nothing（vbObjectError + 1002）
'       - マッピング表の範囲（vMapRng）が Nothing（vbObjectError + 1003）
'       - マッピング表のシート名が、指定したブックに存在しない（vbObjectError + 1004：転記元／1005：転記先）
'       - マッピング表の列位置・開始行が、1 以上の数字でない（vbObjectError + 1007）
'       - マッピング表の列位置・開始行、または転記先の終了行が、シートの上限を超えている（vbObjectError + 1009）
'       - 列の位置の指定が、マッピング表の範囲の列数の外（vbObjectError + 1015）
'     → Setting mistakes stop with an error naming the cause instead of returning False.
'
'   ・Offset / Find / Resize / With は禁止
'     → Offset, Find, Resize, and With statements are prohibited.
'===========================================================

'===========================================================
' ■依存関係（部品名明記） / Component Dependencies
'   ・f_SheetExists（部品_シート存在チェック）が必要
'     → Requires f_SheetExists (SheetExists component).
'       ・マッピング表のシート名が、指定したブックに存在するかの確認に使用
'   ・f_GetLastRow（部品_最終行取得）が必要
'     → Requires f_GetLastRow (GetLastRow component).
'       ・転記元の列の、最終行の取得に使用
'   ・f_SetRange_Fixed（部品_範囲設定_固定）が必要
'     → Requires f_SetRange_Fixed (SetRange_Fixed component).
'       ・転記元の範囲と、転記先の左上セルの作成に使用
'   ・f_CopyRange_Values（部品_範囲コピー_値）が必要
'     → Requires f_CopyRange_Values (CopyRange_Values component).
'       ・1列分の値の転記に使用
'
'   ・組み合わせ：f_SetRange_VariableRows → f_TransferColumn_WithMap
'     （範囲設定_行可変で、マッピング表の範囲を作ってから、渡す）
'     → Typical combination: [SetRange_VariableRows] -> [TransferColumn_WithMap]
'
'   ・組み合わせ：f_OpenFile_ByPath → f_TransferColumn_WithMap
'     （転記先のファイルを開いてから転記する場合。開いた直後に ActiveWorkbook を変数へ控える）
'     → Typical combination: [OpenFile_ByPath] -> [TransferColumn_WithMap]
'===========================================================

'===========================================================
' ■依存関係（シート・表） / Sheet Dependencies
'   ・マッピング表（ユーザーが、事前に記入する）
'     → The mapping table (entered by the user beforehand):
'        転記元シート名・転記元の列位置・転記元の開始行・転記先シート名・転記先の列位置・転記先の開始行
'        / source sheet name, source column, source start row, destination sheet name,
'          destination column, destination start row
'
'   ・列の並びは自由（名称や備考などの列があってよい）。引数の列の位置で、どの列が何かを指定する
'     → The column order is free; the column-position arguments say which column is what.
'===========================================================

'===========================================================
' ■技術解説 / Technical Notes
'
'   ・転記元の最終行を、転記元の列自身で判定する理由
'       → 列ごとにデータの行数が違っても、その列の分だけ転記できる。
'          マッピング表に、最終行を書く必要がない（データが増減しても、表を直さずに済む）。
'       → The last row is detected from the source column itself, so each column is transferred with its own
'          length and the table does not need an end row.
'
'   ・値のみを転記する（Value の代入）理由
'       → Copy メソッドと異なり、書式や入力規則を上書きせず、クリップボードを使わないため高速で安全に動作する。
'       → Assigning Value does not overwrite formatting or validation and does not use the clipboard.
'
'   ・転記の前に、マッピング表の全行を、まとめて確認する理由
'       → シート名の打ち間違いや、列位置・開始行の書き間違いは起きやすい。そのまま転記を始めると、
'          途中まで転記された状態で止まる。そこで、先に全行を確認し、問題があれば、行番号を示すエラーで止める。
'          転記先の終了行が、シートの上限を超えないかも、ここで確認する。
'       → Typos in the table are common; transferring directly would stop with the data half transferred,
'          so all rows (including the destination end row) are checked first.
'
'   ・確認を On Error GoTo より前に置く理由
'       → On Error GoTo ErrHandler の有効な範囲でエラーを出すと、False に変えてしまい、原因が伝わらない。
'          確認を前に置くことで、Err.Raise が呼び出し側へ届く。
'       → Raising inside the range where On Error GoTo is active would turn it into False and hide the cause.
'
'   ・転記できなかった場合に、False を返す理由
'       → 保護されたシートなど、実行時の失敗は、事前には分からない。
'          呼び出し側が、戻り値で確認できるようにして、メッセージやエラー処理は、呼び出し側で調整できるようにしている。
'          原因は、イミディエイトウィンドウ（Ctrl+G）に、Debug.Print で出る（どの行で止まったか、
'          中の部品が出したエラーは、発生元の部品名も出る）。
'       → Run-time failures cannot be known beforehand. The Boolean return value lets the caller check the
'          result; the cause (and the stopped row) is printed to the Immediate window.
'
'   ・Offset / Find / Resize / With を禁止する理由
'       → 生成AIが誤って不正な範囲操作を行う可能性が高く、不明瞭な書き方で誤動作を起こしやすいため。
'       → These statements often cause misaligned or ambiguous range operations when generated by AI.
'
'   ・この部品の位置づけ
'       → マッピング表で指定する「転記（Transfer）」のうち、列単位の部品。
'          行数が可変の、複数の列をまとめて転記したいときは、この部品を標準として選ぶ。
'       → The column-based component among the mapping-table "Transfer" components.
'
'   ・本部品が「応用」である理由
'       → 土台の部品（シート存在チェック・最終行取得・範囲設定_固定・範囲コピー_値）を参照するため。
'       → It references foundation components.
'===========================================================

'---------------------------------------------
' ■引数（型＋意味） / Arguments
'   vSrcWb          : 転記元のブック（Workbook）／必須（省略できない）
'                     → Source workbook (Workbook); required.
'
'   vDstWb          : 転記先のブック（Workbook）／必須（省略できない）
'                     → Destination workbook (Workbook); required.
'
'   vMapRng         : マッピング表の範囲（Range）。見出し行を含まない、データの行だけ
'                     → Range of the mapping table (Range); data rows only, without the header row.
'
'   vColSrcSheet    : 転記元のシート名が入っている列の位置（Long）。範囲の左端を 1 とした番号
'                     → Position of the column holding the source sheet name (Long); left-most column = 1.
'
'   vColSrcStartRow : 転記元の「開始行」が入っている列の位置（Long）
'                     → Position of the column holding the source start row (Long).
'
'   vColSrcCol      : 転記元の「列位置」が入っている列の位置（Long）
'                     → Position of the column holding the source column number (Long).
'
'   vColDstSheet    : 転記先のシート名が入っている列の位置（Long）
'                     → Position of the column holding the destination sheet name (Long).
'
'   vColDstStartRow : 転記先の「開始行」が入っている列の位置（Long）
'                     → Position of the column holding the destination start row (Long).
'
'   vColDstCol      : 転記先の「列位置」が入っている列の位置（Long）
'                     → Position of the column holding the destination column number (Long).
'---------------------------------------------

'---------------------------------------------
' ■戻り値（型＋意味） / Return Value
'   Boolean : 転記できた場合は True、実行時にできなかった場合は False
'             → True if transferred, False if it failed at run time.
'---------------------------------------------

'---------------------------------------------
' ■エラー / Errors (Err.Raise)
'   ・vbObjectError + 1001：転記元ブック（vSrcWb）が Nothing
'   ・vbObjectError + 1002：転記先ブック（vDstWb）が Nothing
'   ・vbObjectError + 1003：マッピング表の範囲（vMapRng）が Nothing
'   ・vbObjectError + 1004：マッピング表の転記元シート名が、転記元ブックに存在しない
'   ・vbObjectError + 1005：マッピング表の転記先シート名が、転記先ブックに存在しない
'   ・vbObjectError + 1007：マッピング表の列位置・開始行が、1 以上の数字でない
'   ・vbObjectError + 1009：マッピング表の列位置・開始行、または転記先の終了行が、シートの上限を超えている
'   ・vbObjectError + 1015：列の位置の指定が、マッピング表の範囲の列数の外（1 未満、または列数より大きい）
'---------------------------------------------

'===========================================================
' ■禁止事項（AI向け） / Prohibitions
'   ・Function を Sub（プロシージャ）に変更することの禁止
'     → Do not convert this Function into a Sub; the Boolean return value is essential.
'
'   ・戻り値（Boolean）を確認せずに後続処理を行うことの禁止
'     → Do not proceed to the following processing without checking the Boolean return value.
'
'   ・マッピング表の確認（シート存在チェックなど）を省略することの禁止
'     → Do not skip the check of the mapping table.
'
'   ・転記元・転記先のブックを省略することの禁止（必ず引数で指定する）
'     → Do not omit the source/destination workbooks; always specify them.
'
'   ・ブックを指定せずに、Worksheets("名前") でシートを取得することの禁止
'     （ThisWorkbook. または、ブックを入れた変数を付ける）
'     → Do not get a sheet with a bare Worksheets("name"); prefix it with a workbook.
'
'   ・列の位置を、シート上の列番号（A 列＝1 など）と取り違えることの禁止
'     （範囲の左端の列を 1 とした番号で指定する）
'     → Do not confuse the column positions with sheet column numbers; count from the left-most column of
'        the range as 1.
'
'   ・マッピング表の範囲に、見出し行を含めることの禁止
'     → Do not include the header row in the mapping range.
'
'   ・転記元・転記先の対応を、コード内に直書きすることの禁止
'     → Do not hard-code source/destination pairs in the code; always use the mapping table.
'
'   ・セル参照の直書き禁止（Range("A1") など）
'     → Hard-coded cell references are prohibited.
'
'   ・Offset禁止 / Find禁止 / Resize禁止 / With禁止
'     → Offset, Find, Resize, and With blocks are prohibited.
'===========================================================

'===========================================================
' ■使用例（サンプルコード） / Example
'   ◆例1：同じブック内で転記する / Example 1: transfer within the same workbook◆
'   Dim map As Range
'
'   Set map = 部品_範囲設定_行可変(ThisWorkbook, "マッピング表", 2, 1, 7, 2)   '2行目から、A-G列。最終行は2列目（転記元シート名）で判定
'   If map Is Nothing Then
'       MsgBox "マッピング表にデータがありません"
'       Exit Sub
'   End If
'
'   If 部品_転記_列単位(ThisWorkbook, ThisWorkbook, map, 2, 3, 4, 5, 6, 7) = False Then
'       MsgBox "転記に失敗しました（シートの保護などを確認してください）"
'       Exit Sub
'   End If
'
'   ◆例2：開いたファイルへ転記する / Example 2: transfer into an opened file◆
'   Dim wbDst As Workbook
'
'   If 部品_ファイルを開く("E:\TEST\テンプレート.xlsx") = False Then Exit Sub
'   Set wbDst = ActiveWorkbook                               '開いた直後に控える / keep it right after opening
'
'   Set map = 部品_範囲設定_行可変(ThisWorkbook, "マッピング表", 2, 1, 7, 2)
'   If map Is Nothing Then MsgBox "マッピング表にデータがありません": Exit Sub
'   If 部品_転記_列単位(ThisWorkbook, wbDst, map, 2, 3, 4, 5, 6, 7) = False Then MsgBox "転記に失敗しました": Exit Sub
'
'   ◆マッピング表の例 / Mapping table example◆
'   名称 | 転記元シート名 | 転記元開始行 | 転記元列位置 | 転記先シート名 | 転記先開始行 | 転記先列位置
'   内容 | 例1_転記元     | 2            | 2            | 例1_転記先     | 14           | 2
'   数量 | 例2_転記元     | 2            | 3            | 例2_転記先     | 14           | 10
'
'   ※ 設定の誤り（Nothing、シート名の誤り、列位置・開始行の誤り、列の位置の誤り）の場合は、False ではなく、
'      原因を示すエラーで止まる（起点で On Error で受けて、Err.Description を表示する）
'===========================================================

'===========================================================
' ■ラッパー関数（日本語名） / Wrapper Function
'   ・辞書の日本語名で呼び出すための窓口
'     → Entry point callable by the Japanese dictionary name.
'
'   ・内部では英語名の本体処理を呼び出し、結果（Boolean）をそのまま返す
'     → Internally calls the English-named core function and returns its result (Boolean) as it is.
'===========================================================
Function 部品_転記_列単位( _
        ByVal vSrcWb As Workbook, _
        ByVal vDstWb As Workbook, _
        ByVal vMapRng As Range, _
        ByVal vColSrcSheet As Long, _
        ByVal vColSrcStartRow As Long, _
        ByVal vColSrcCol As Long, _
        ByVal vColDstSheet As Long, _
        ByVal vColDstStartRow As Long, _
        ByVal vColDstCol As Long) As Boolean

    '本体処理（英語名）を呼び出し、結果をそのまま返す / Call core function and return its result
    部品_転記_列単位 = f_TransferColumn_WithMap(vSrcWb, vDstWb, vMapRng, _
                                              vColSrcSheet, vColSrcStartRow, vColSrcCol, _
                                              vColDstSheet, vColDstStartRow, vColDstCol)

End Function

'===========================================================
' ■本体処理（英語名） / Core Function
'   ・マッピング表の各行に従い、転記元の列を、最終行まで、転記先の列へ転記する（値のみ）
'     → Transfers a column of values for each row of the mapping table, down to the last row.
'
'   ・転記できた場合：True、実行時にできなかった場合：False を返す
'     → Returns True if transferred and False if it failed at run time.
'===========================================================
Function f_TransferColumn_WithMap( _
        ByVal vSrcWb As Workbook, _
        ByVal vDstWb As Workbook, _
        ByVal vMapRng As Range, _
        ByVal vColSrcSheet As Long, _
        ByVal vColSrcStartRow As Long, _
        ByVal vColSrcCol As Long, _
        ByVal vColDstSheet As Long, _
        ByVal vColDstStartRow As Long, _
        ByVal vColDstCol As Long) As Boolean

    Const cActiveSheet As String = "ActiveSheet"

    Dim i As Long
    Dim mapRowCount As Long
    Dim mapRowNo As Long
    Dim srcActiveName As String
    Dim dstActiveName As String
    Dim srcSheetName As String
    Dim dstSheetName As String
    Dim srcCol As Long
    Dim srcStartRow As Long
    Dim srcLastRow As Long
    Dim dstCol As Long
    Dim dstStartRow As Long
    Dim dstEndRow As Long
    Dim srcRng As Range
    Dim dstTopLeft As Range

    f_TransferColumn_WithMap = False

    '---------------------------------------------
    ' ■ブック・マッピング表の範囲が設定されているかを確認（Nothing の場合はエラーで止める）
    '   ※ On Error GoTo より前に置く（Err.Raise を False に変えず、呼び出し側へ届けるため）
    '   / Check that the workbooks and the mapping range are set (stop with an error if Nothing);
    '     placed before On Error GoTo so that Err.Raise reaches the caller
    '---------------------------------------------
    If vSrcWb Is Nothing Then
        Err.Raise vbObjectError + 1001, "f_TransferColumn_WithMap", _
                  "転記元のブック（vSrcWb）が設定されていません（Nothing）。"
    End If

    If vDstWb Is Nothing Then
        Err.Raise vbObjectError + 1002, "f_TransferColumn_WithMap", _
                  "転記先のブック（vDstWb）が設定されていません（Nothing）。"
    End If

    If vMapRng Is Nothing Then
        Err.Raise vbObjectError + 1003, "f_TransferColumn_WithMap", _
                  "マッピング表の範囲（vMapRng）が設定されていません（Nothing）。"
    End If

    '---------------------------------------------
    ' ■列の位置が、マッピング表の範囲の中にあるかを確認（外の場合はエラーで止める）
    '   / Check that the column positions are inside the mapping range (stop with an error if not)
    '---------------------------------------------
    If vColSrcSheet < 1 Or vColSrcSheet > vMapRng.Columns.Count Or _
       vColSrcStartRow < 1 Or vColSrcStartRow > vMapRng.Columns.Count Or _
       vColSrcCol < 1 Or vColSrcCol > vMapRng.Columns.Count Or _
       vColDstSheet < 1 Or vColDstSheet > vMapRng.Columns.Count Or _
       vColDstStartRow < 1 Or vColDstStartRow > vMapRng.Columns.Count Or _
       vColDstCol < 1 Or vColDstCol > vMapRng.Columns.Count Then
        Err.Raise vbObjectError + 1015, "f_TransferColumn_WithMap", _
                  "列の位置は、マッピング表の範囲の列数（" & vMapRng.Columns.Count & "列）の中で、" & _
                  "左端を 1 として指定してください" & _
                  "（転記元シート名=" & vColSrcSheet & "、転記元開始行=" & vColSrcStartRow & "、転記元列位置=" & vColSrcCol & _
                  "、転記先シート名=" & vColDstSheet & "、転記先開始行=" & vColDstStartRow & "、転記先列位置=" & vColDstCol & "）。"
    End If

    '---------------------------------------------
    ' ■"ActiveSheet" が指すシート名を取得（転記の前に 1 回だけ）
    '   / Get the sheet names that "ActiveSheet" stands for (once, before transferring)
    '---------------------------------------------
    srcActiveName = vSrcWb.ActiveSheet.Name
    dstActiveName = vDstWb.ActiveSheet.Name

    mapRowCount = vMapRng.Rows.Count

    '---------------------------------------------
    ' ■転記を始める前に、マッピング表の全行を確認する
    '   1行でも問題があれば、1列も転記せずに、行番号を示すエラーで止める
    '   / Before transferring, check ALL mapping rows; if any row is wrong, stop with an error naming the
    '     row without transferring anything
    '---------------------------------------------
    For i = 1 To mapRowCount

        mapRowNo = vMapRng.Row + i - 1                          'マッピング表の、シート上の行番号 / row number on the sheet

        srcSheetName = CStr(vMapRng.Cells(i, vColSrcSheet).Value)
        dstSheetName = CStr(vMapRng.Cells(i, vColDstSheet).Value)
        If StrComp(srcSheetName, cActiveSheet, vbTextCompare) = 0 Then srcSheetName = srcActiveName
        If StrComp(dstSheetName, cActiveSheet, vbTextCompare) = 0 Then dstSheetName = dstActiveName

        If f_SheetExists(vSrcWb, srcSheetName) = False Then
            Err.Raise vbObjectError + 1004, "f_TransferColumn_WithMap", _
                      "マッピング表の" & mapRowNo & "行目：転記元シート「" & srcSheetName & _
                      "」が、ブック「" & vSrcWb.Name & "」に存在しません。"
        End If

        If f_SheetExists(vDstWb, dstSheetName) = False Then
            Err.Raise vbObjectError + 1005, "f_TransferColumn_WithMap", _
                      "マッピング表の" & mapRowNo & "行目：転記先シート「" & dstSheetName & _
                      "」が、ブック「" & vDstWb.Name & "」に存在しません。"
        End If

        If IsNumeric(vMapRng.Cells(i, vColSrcCol).Value) = False Or _
           IsNumeric(vMapRng.Cells(i, vColSrcStartRow).Value) = False Or _
           IsNumeric(vMapRng.Cells(i, vColDstCol).Value) = False Or _
           IsNumeric(vMapRng.Cells(i, vColDstStartRow).Value) = False Then
            Err.Raise vbObjectError + 1007, "f_TransferColumn_WithMap", _
                      "マッピング表の" & mapRowNo & "行目：列位置・開始行は、1 以上の数字で書いてください。"
        End If

        srcCol = CLng(vMapRng.Cells(i, vColSrcCol).Value)
        srcStartRow = CLng(vMapRng.Cells(i, vColSrcStartRow).Value)
        dstCol = CLng(vMapRng.Cells(i, vColDstCol).Value)
        dstStartRow = CLng(vMapRng.Cells(i, vColDstStartRow).Value)

        If srcCol < 1 Or srcStartRow < 1 Or dstCol < 1 Or dstStartRow < 1 Then
            Err.Raise vbObjectError + 1007, "f_TransferColumn_WithMap", _
                      "マッピング表の" & mapRowNo & "行目：列位置・開始行は、1 以上の数字で書いてください" & _
                      "（転記元の列=" & srcCol & "、開始行=" & srcStartRow & _
                      "、転記先の列=" & dstCol & "、開始行=" & dstStartRow & "）。"
        End If

        If srcCol > vSrcWb.Worksheets(srcSheetName).Columns.Count Or _
           srcStartRow > vSrcWb.Worksheets(srcSheetName).Rows.Count Or _
           dstCol > vDstWb.Worksheets(dstSheetName).Columns.Count Or _
           dstStartRow > vDstWb.Worksheets(dstSheetName).Rows.Count Then
            Err.Raise vbObjectError + 1009, "f_TransferColumn_WithMap", _
                      "マッピング表の" & mapRowNo & "行目：列位置・開始行が、シートの上限を超えています" & _
                      "（転記元の列=" & srcCol & "、開始行=" & srcStartRow & _
                      "、転記先の列=" & dstCol & "、開始行=" & dstStartRow & "）。"
        End If

        '転記先の終了行が、シートの上限を超えないかを確認 / Check that the destination end row stays within the sheet
        srcLastRow = f_GetLastRow(vSrcWb, srcSheetName, srcCol)
        If srcLastRow >= srcStartRow Then
            dstEndRow = dstStartRow + (srcLastRow - srcStartRow)
            If dstEndRow > vDstWb.Worksheets(dstSheetName).Rows.Count Then
                Err.Raise vbObjectError + 1009, "f_TransferColumn_WithMap", _
                          "マッピング表の" & mapRowNo & "行目：転記先の終了行が、シートの上限（" & _
                          vDstWb.Worksheets(dstSheetName).Rows.Count & "行）を超えます（終了行=" & dstEndRow & "）。"
            End If
        End If

    Next i

    '---------------------------------------------
    ' ■エラー時は ErrHandler へ（False を返す） / On error, jump to ErrHandler (returns False)
    '---------------------------------------------
    On Error GoTo ErrHandler

    '---------------------------------------------
    ' ■マッピング表の行ループ（1行＝1列分を、値のみ転記） / Mapping row loop (transfer one column per row)
    '---------------------------------------------
    For i = 1 To mapRowCount

        mapRowNo = vMapRng.Row + i - 1

        srcSheetName = CStr(vMapRng.Cells(i, vColSrcSheet).Value)
        dstSheetName = CStr(vMapRng.Cells(i, vColDstSheet).Value)
        If StrComp(srcSheetName, cActiveSheet, vbTextCompare) = 0 Then srcSheetName = srcActiveName
        If StrComp(dstSheetName, cActiveSheet, vbTextCompare) = 0 Then dstSheetName = dstActiveName

        srcCol = CLng(vMapRng.Cells(i, vColSrcCol).Value)
        srcStartRow = CLng(vMapRng.Cells(i, vColSrcStartRow).Value)
        dstCol = CLng(vMapRng.Cells(i, vColDstCol).Value)
        dstStartRow = CLng(vMapRng.Cells(i, vColDstStartRow).Value)

        srcLastRow = f_GetLastRow(vSrcWb, srcSheetName, srcCol)

        '開始行以降にデータが無い列は、何もせず次の行へ / If no data at or below the start row, skip this row
        If srcLastRow >= srcStartRow Then

            Set srcRng = f_SetRange_Fixed(vSrcWb, srcSheetName, srcStartRow, srcCol, srcLastRow, srcCol)
            Set dstTopLeft = f_SetRange_Fixed(vDstWb, dstSheetName, dstStartRow, dstCol, dstStartRow, dstCol)

            If f_CopyRange_Values(srcRng, dstTopLeft) = False Then
                Debug.Print "f_TransferColumn_WithMap: マッピング表の" & mapRowNo & "行目で、転記に失敗したため、止めました。"
                Exit Function                                   'False のまま返す / return False as it is
            End If

        End If

    Next i

    f_TransferColumn_WithMap = True
    Exit Function

ErrHandler:
    Debug.Print "f_TransferColumn_WithMap: " & Err.Number & " " & Err.Description & "（発生元：" & Err.Source & "）"
    f_TransferColumn_WithMap = False

End Function

