@@ -13,6 +13,10 @@ import UploadMarkdown from "./uploadMarkdown";
1313import UploadImage from "./uploadImage" ;
1414
1515type positionInfo = null | { top : number ; left : number } ;
16+ type TabAreaArgs = {
17+ e : React . KeyboardEvent < HTMLTextAreaElement > ;
18+ ref : React . MutableRefObject < HTMLTextAreaElement | null > ;
19+ } ;
1620
1721export default function App ( ) {
1822 const [ markdown , setMarkdown ] = useState ( "" ) ;
@@ -30,6 +34,26 @@ export default function App() {
3034 const inputRef = useRef < HTMLTextAreaElement | null > ( null ) ;
3135 const previewRef = useRef < HTMLDivElement | null > ( null ) ;
3236
37+ const handleTabArea = ( { e, ref } : TabAreaArgs ) => {
38+ if ( e . key !== "Tab" ) return ; // Tabキー以外は処理しない
39+
40+ e . preventDefault ( ) ; // デフォルトのタブ挿入動作を止める
41+
42+ if ( ! ref . current ) return ;
43+
44+ const textarea = ref . current ;
45+ const cursorPosition = textarea . selectionStart ;
46+ const cursorLeft = textarea . value . substring ( 0 , cursorPosition ) ;
47+ const cursorRight = textarea . value . substring ( cursorPosition ) ;
48+
49+ // タブの代わりに半角スペース3つを挿入
50+ const tabSpaces = " " ;
51+ textarea . value = cursorLeft + tabSpaces + cursorRight ;
52+
53+ // カーソルを3文字分進める
54+ textarea . selectionStart = textarea . selectionEnd = cursorPosition + 3 ;
55+ } ;
56+
3357 // 2/3追加・テンプレート部分
3458
3559 const [ buttonName , setButtonName ] = useState < string [ ] > ( [
@@ -273,6 +297,7 @@ export default function App() {
273297 onScroll = { ( ) => handleScrollSync ( textAreaRef , previewRef ) }
274298 onChange = { ( event ) => setMarkdown ( event . target . value ) }
275299 placeholder = "編集画面"
300+ onKeyDown = { ( e ) => handleTabArea ( { e, ref : textAreaRef } ) } // ここ
276301 onFocus = { ( ) => setIsTextAreaFocused ( true ) }
277302 onBlur = { ( ) => setIsTextAreaFocused ( false ) }
278303 />
@@ -287,6 +312,7 @@ export default function App() {
287312 value = { inputValue }
288313 ref = { inputRef }
289314 onChange = { handleInputChange }
315+ onKeyDown = { ( e ) => handleTabArea ( { e, ref : inputRef } ) } // ここ
290316 style = { {
291317 position : "absolute" ,
292318 top : `${ inputPosition . top } px` ,
0 commit comments