type8 ms_getchar(type8 trans) { bool done = false; char c = 0; do { CMagneticView* pView = CMagneticView::GetView(); if (pView == NULL) return 1; if (pView->GetRecording() == CMagneticView::Recording::PlaybackOn) { if (pView->GetRecordFile()) { CMagneticApp* pApp = (CMagneticApp*)AfxGetApp(); if (pApp->GetAnimWait()) { while (pView->GetAnimate() && (ms_anim_is_repeating() == 0)) { if (pApp->PumpMessage() == FALSE) { ::PostQuitMessage(0); return 1; } pApp->CWinApp::OnIdle(0); } } char cInput = CMagneticView::GetPlaybackChar(pView->GetRecordFile()); if (feof(pView->GetRecordFile()) != 0) { pView->SetRecording(CMagneticView::Recording::RecordingOff); fclose(pView->GetRecordFile()); pView->SetRecordFile(NULL); pView->ClearPagination(); } else { if (cInput == '\n') { cInput = 10; pView->TrimOutput(); pView->GetPageTable().RemoveAll(); pView->Invalidate(); } else pView->AddOutChar(cInput); return cInput; } } } c = CMagneticView::GetInput(done,trans != 0); } while (done == false); return c; }
char CMagneticView::GetInput(bool& done, bool trans) { static const int MAX_HISTORY = 20; done = true; CMagneticApp* pApp = (CMagneticApp*)AfxGetApp(); CMagneticView* pView = CMagneticView::GetView(); if (pView == NULL) return 0; int cInput = 0; // Input character int iPosition = 0; // Current cursor position int iHistory = -1; // Current history position static CString strFullLine; // Input line already obtained? if (strFullLine.GetLength() > 0) { cInput = strFullLine[0]; strFullLine = strFullLine.Right(strFullLine.GetLength()-1); if (cInput == (signed char)(CMagneticView::SPECIAL_KEYS + VK_SPACE)) cInput = ' '; return (char)cInput; } if (pView->m_bMorePrompt) pView->m_PageTable.RemoveAt(pView->m_PageTable.GetSize()-1); else pView->m_PageTable.RemoveAll(); // Refresh the view pView->Invalidate(); pView->CaretOn(); pView->m_bInputActive = true; while (cInput != 10 && cInput != 1) { pView = CMagneticView::GetView(); if (pView == NULL) break; // Wait for a character CArray<int, int>& Input = pView->m_Input; if (Input.GetSize() == 0) { pApp->PumpMessage(); pApp->CWinApp::OnIdle(0); // Call base class OnIdle(); pView = CMagneticView::GetView(); if (pView) { CMagneticApp::Redraw Status = pApp->GetRedrawStatus(); switch (Status) { case CMagneticApp::Redraw::EndPlayback: done = false; // intentional fall-through case CMagneticApp::Redraw::EndLine: case CMagneticApp::Redraw::EndOpcode: Input.RemoveAll(); strFullLine.Empty(); if (Status == CMagneticApp::Redraw::EndOpcode) cInput = 1; else cInput = 10; // intentional fall-through case CMagneticApp::Redraw::ThisLine: pView->CaretOff(); pView->CaretOn(); pView->Invalidate(); break; } pView->SetCursorPos(pView->m_pTextDC,strFullLine.GetLength()-iPosition); } } else { cInput = (pView->m_bMorePrompt) ? 10 : Input[0]; Input.RemoveAt(0); int iInsertPos, iRemovePos; switch (cInput) { case 10: // Return strFullLine += (char)cInput; break; case CMagneticView::SPECIAL_KEYS + VK_LEFT: // Cursor left if (iPosition > 0) iPosition--; break; case CMagneticView::SPECIAL_KEYS + VK_RIGHT: // Cursor right if (iPosition < strFullLine.GetLength()) iPosition++; break; case CMagneticView::SPECIAL_KEYS + VK_HOME: // Home iPosition = 0; break; case CMagneticView::SPECIAL_KEYS + VK_END: // End iPosition = strFullLine.GetLength(); break; case CMagneticView::SPECIAL_KEYS + VK_DELETE: // Delete if (iPosition < strFullLine.GetLength()) { iRemovePos = strFullLine.GetLength() - iPosition; pView->RemoveChar(strFullLine,iRemovePos); pView->RemoveChar(pView->m_strOutput,iRemovePos,TRUE); } break; case 8: // Backspace if (iPosition > 0) { iRemovePos = strFullLine.GetLength() - iPosition + 1; pView->RemoveChar(strFullLine,iRemovePos); pView->RemoveChar(pView->m_strOutput,iRemovePos,TRUE); iPosition--; } break; case CMagneticView::SPECIAL_KEYS + VK_UP: // Cursor up if (iHistory < pView->m_History.GetSize()-1) iHistory++; if ((iHistory >= 0) && (pView->m_History.GetSize() > 0)) { int iOldLength = strFullLine.GetLength(); strFullLine = pView->m_History[iHistory]; pView->UseHistory(strFullLine,iOldLength); iPosition = strFullLine.GetLength(); } break; case CMagneticView::SPECIAL_KEYS + VK_DOWN: // Cursor down if (iHistory > 0) iHistory--; if ((iHistory >= 0) && (pView->m_History.GetSize() > 0)) { int iOldLength = strFullLine.GetLength(); strFullLine = pView->m_History[iHistory]; pView->UseHistory(strFullLine,iOldLength); iPosition = strFullLine.GetLength(); } break; case CMagneticView::SPECIAL_KEYS + VK_SPACE: // Space iInsertPos = strFullLine.GetLength() - iPosition; pView->InsertChar(pView->m_strOutput,(char)cInput,iInsertPos,TRUE); pView->InsertChar(strFullLine,(char)cInput,iInsertPos); iPosition++; break; default: if (isprint(cInput) && (cInput < CMagneticView::SPECIAL_KEYS)) { // Insert the character into the input string iInsertPos = strFullLine.GetLength() - iPosition; pView->InsertChar(pView->m_strOutput,(char)cInput,iInsertPos,TRUE); pView->InsertChar(strFullLine,(char)cInput,iInsertPos); iPosition++; } break; } // Update the input line pView->InvalidateRect(pView->m_LastLineRect,FALSE); } } if (pView && (strFullLine.GetLength() > 0)) { if (pView->m_bMorePrompt == false) { // Store in input history CString strHistory = strFullLine.Left(strFullLine.GetLength()-1); if (strHistory.GetLength() > 0) { pView->m_History.InsertAt(0,strHistory); if (pView->m_History.GetSize() > MAX_HISTORY) pView->m_History.RemoveAt(pView->m_History.GetSize()-1); } int i; while ((i = strHistory.Find((char)(CMagneticView::SPECIAL_KEYS + VK_SPACE))) >= 0) strHistory.SetAt(i,' '); // Input recording if ((pView->m_Recording == Recording::RecordingOn) && (pView->m_pFileRecord)) fprintf(pView->m_pFileRecord,"%s\n",strHistory); // Scrollback buffer pView->m_Scrollback.GetScrollback() += strHistory; // Scripting if (pView->m_Scripting == Scripting::ScriptingOn) pView->m_strScript += strHistory; } if (trans && (strFullLine.CompareNoCase("#undo\n") == 0)) { cInput = 0; strFullLine.Empty(); } else { cInput = strFullLine[0]; strFullLine = strFullLine.Right(strFullLine.GetLength()-1); } } if (pView) { pView->m_iLines = 0; pView->m_bInputActive = false; pView->CaretOff(); } if (cInput == (signed char)(CMagneticView::SPECIAL_KEYS + VK_SPACE)) cInput = ' '; return (char)cInput; }