Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

946 lines
25 KiB

  1. /*++
  2. Copyright (c) 1999 Intel Corporation
  3. Module Name:
  4. libFileBuffer.c
  5. Abstract:
  6. Defines FileBuffer - the view of the file that is visible at any point,
  7. as well as the event handlers for editing the file
  8. --*/
  9. #ifndef _LIB_FILE_BUFFER
  10. #define _LIB_FILE_BUFFER
  11. #include "libMisc.h"
  12. extern EFI_EDITOR_LINE* FileImageCreateNode (VOID);
  13. #define ABSOLUTE_MAX_COLUMNS 132
  14. STATIC CHAR16 BlankLine[ABSOLUTE_MAX_COLUMNS];
  15. STATIC EFI_STATUS FileBufferScrollUp (VOID);
  16. STATIC EFI_STATUS FileBufferScrollDown (VOID);
  17. STATIC EFI_STATUS FileBufferScrollLeft (VOID);
  18. STATIC EFI_STATUS FileBufferScrollRight (VOID);
  19. STATIC EFI_STATUS FileBufferPageUp (VOID);
  20. STATIC EFI_STATUS FileBufferPageDown (VOID);
  21. STATIC EFI_STATUS FileBufferHome (VOID);
  22. STATIC EFI_STATUS FileBufferEnd (VOID);
  23. STATIC EFI_STATUS FileBufferChangeMode (VOID);
  24. STATIC EFI_STATUS FileBufferDoDelete (VOID);
  25. STATIC EFI_STATUS FileBufferDoBackspace (VOID);
  26. STATIC EFI_STATUS FileBufferDoCharInput (CHAR16);
  27. STATIC EFI_STATUS FileBufferDoReturn (VOID);
  28. STATIC EFI_STATUS FileBufferRefreshCurrentLine(VOID);
  29. STATIC EFI_STATUS FileBufferRefreshDown(VOID);
  30. STATIC EFI_STATUS FileBufferInit (VOID);
  31. STATIC EFI_STATUS FileBufferCleanup (VOID);
  32. STATIC EFI_STATUS FileBufferRefresh (VOID);
  33. STATIC EFI_STATUS FileBufferHide (VOID);
  34. STATIC EFI_STATUS FileBufferHandleInput (EFI_INPUT_KEY*);
  35. STATIC EFI_STATUS FileBufferClearLine (UINTN);
  36. STATIC EFI_STATUS FileBufferSetPosition (UINTN,UINTN);
  37. STATIC EFI_STATUS FileBufferRestorePosition (VOID);
  38. EFI_EDITOR_FILE_BUFFER FileBuffer = {
  39. {0,0},
  40. {0,0},
  41. {0,0},
  42. {0,0},
  43. 0,
  44. 0,
  45. TRUE,
  46. NULL,
  47. FileBufferInit,
  48. FileBufferCleanup,
  49. FileBufferRefresh,
  50. FileBufferHide,
  51. FileBufferHandleInput,
  52. FileBufferClearLine,
  53. FileBufferSetPosition,
  54. FileBufferRestorePosition,
  55. FileBufferRefreshCurrentLine
  56. };
  57. EFI_EDITOR_FILE_BUFFER FileBufferConst = {
  58. {0,0},
  59. {0,0},
  60. {0,0},
  61. {0,0},
  62. 0,
  63. 0,
  64. TRUE,
  65. NULL,
  66. FileBufferInit,
  67. FileBufferCleanup,
  68. FileBufferRefresh,
  69. FileBufferHide,
  70. FileBufferHandleInput,
  71. FileBufferClearLine,
  72. FileBufferSetPosition,
  73. FileBufferRestorePosition,
  74. FileBufferRefreshCurrentLine
  75. };
  76. STATIC
  77. EFI_STATUS
  78. FileBufferInit (
  79. VOID
  80. )
  81. {
  82. UINTN i;
  83. CopyMem (&FileBuffer, &FileBufferConst, sizeof(FileBuffer));
  84. FileBuffer.DisplayPosition.Row = TEXT_START_ROW;
  85. FileBuffer.DisplayPosition.Column = TEXT_START_COLUMN;
  86. FileBuffer.LowVisibleRange.Row = TEXT_START_ROW;
  87. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  88. FileBuffer.MaxVisibleRows = MAX_TEXT_ROWS;
  89. FileBuffer.MaxVisibleColumns = MAX_TEXT_COLUMNS;
  90. FileBuffer.HighVisibleRange.Row = MAX_TEXT_ROWS;
  91. FileBuffer.HighVisibleRange.Column = MAX_TEXT_COLUMNS;
  92. for (i = 0; i < MAX_TEXT_COLUMNS; i++) {
  93. BlankLine[i] = ' ';
  94. }
  95. BlankLine[i-1] = 0;
  96. FileBuffer.LowVisibleRange.Row = TEXT_START_ROW;
  97. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  98. FileBuffer.MaxVisibleRows = MAX_TEXT_ROWS;
  99. FileBuffer.MaxVisibleColumns = MAX_TEXT_COLUMNS;
  100. FileBuffer.FilePosition.Row = 1;
  101. FileBuffer.FilePosition.Column = 1;
  102. return EFI_SUCCESS;
  103. }
  104. STATIC
  105. EFI_STATUS
  106. FileBufferCleanup (
  107. VOID
  108. )
  109. {
  110. return EFI_SUCCESS;
  111. }
  112. STATIC
  113. EFI_STATUS
  114. FileBufferRefresh (
  115. VOID
  116. )
  117. {
  118. LIST_ENTRY *Item;
  119. UINTN Row;
  120. Row = FileBuffer.DisplayPosition.Row;
  121. FileBuffer.DisplayPosition.Row = TEXT_START_ROW;
  122. Item = FileBuffer.CurrentLine;
  123. LineRetreat(FileBuffer.FilePosition.Row - FileBuffer.LowVisibleRange.Row);
  124. FileBufferRefreshDown();
  125. FileBuffer.CurrentLine = Item;
  126. FileBuffer.DisplayPosition.Row = Row;
  127. FileBufferRestorePosition();
  128. return EFI_SUCCESS;
  129. }
  130. STATIC
  131. EFI_STATUS
  132. FileBufferRefreshCurrentLine (
  133. VOID
  134. )
  135. {
  136. EFI_EDITOR_LINE *Line;
  137. UINTN Where;
  138. CHAR16 *StrLine;
  139. UINTN StartColumn;
  140. Where = FileBuffer.DisplayPosition.Row;
  141. StartColumn = FileBuffer.LowVisibleRange.Column;
  142. FileBufferClearLine(Where);
  143. Line = LineCurrent();
  144. if (Line->Link.Blink == MainEditor.FileImage->ListHead &&
  145. FileBuffer.DisplayPosition.Row > TEXT_START_ROW) {
  146. return EFI_SUCCESS;
  147. }
  148. if (Line->Size < StartColumn) {
  149. FileBufferRestorePosition();
  150. return EFI_SUCCESS;
  151. }
  152. StrLine = PoolPrint(L"%s",Line->Buffer + StartColumn);
  153. if ((Line->Size - StartColumn)> FileBuffer.MaxVisibleColumns) {
  154. StrLine[FileBuffer.MaxVisibleColumns-2] = 0;
  155. } else {
  156. StrLine[(Line->Size - StartColumn)] = 0;
  157. }
  158. /* PrintAt(0,Where,StrLine); */
  159. Out->SetCursorPosition(Out,0,Where);
  160. Out->OutputString(Out,StrLine);
  161. FreePool(StrLine);
  162. FileBufferRestorePosition();
  163. return EFI_SUCCESS;
  164. }
  165. STATIC
  166. EFI_STATUS
  167. FileBufferRefreshDown (
  168. VOID
  169. )
  170. {
  171. LIST_ENTRY *Item;
  172. LIST_ENTRY *Link;
  173. UINTN Row;
  174. Row = FileBuffer.DisplayPosition.Row;
  175. Item = FileBuffer.CurrentLine;
  176. Link = FileBuffer.CurrentLine;
  177. while (FileBuffer.DisplayPosition.Row <= MAX_TEXT_ROWS) {
  178. if (Link->Flink != MainEditor.FileImage->ListHead) {
  179. FileBufferRefreshCurrentLine();
  180. LineNext();
  181. Link = FileBuffer.CurrentLine;
  182. } else {
  183. FileBufferClearLine(FileBuffer.DisplayPosition.Row);
  184. }
  185. FileBuffer.DisplayPosition.Row++;
  186. }
  187. FileBuffer.CurrentLine = Item;
  188. FileBuffer.DisplayPosition.Row = Row;
  189. FileBufferRestorePosition();
  190. return EFI_SUCCESS;
  191. }
  192. STATIC
  193. EFI_STATUS
  194. FileBufferHandleInput (
  195. IN EFI_INPUT_KEY* Key
  196. )
  197. {
  198. switch (Key->ScanCode) {
  199. case SCAN_CODE_NULL:
  200. FileBufferDoCharInput (Key->UnicodeChar);
  201. break;
  202. case SCAN_CODE_UP:
  203. FileBufferScrollUp();
  204. break;
  205. case SCAN_CODE_DOWN:
  206. FileBufferScrollDown();
  207. break;
  208. case SCAN_CODE_RIGHT:
  209. FileBufferScrollRight();
  210. break;
  211. case SCAN_CODE_LEFT:
  212. FileBufferScrollLeft();
  213. break;
  214. case SCAN_CODE_PGUP:
  215. FileBufferPageUp();
  216. break;
  217. case SCAN_CODE_PGDN:
  218. FileBufferPageDown();
  219. break;
  220. case SCAN_CODE_DEL:
  221. FileBufferDoDelete();
  222. break;
  223. case SCAN_CODE_HOME:
  224. FileBufferHome();
  225. break;
  226. case SCAN_CODE_END:
  227. FileBufferEnd();
  228. break;
  229. case SCAN_CODE_INS:
  230. FileBufferChangeMode();
  231. break;
  232. default:
  233. break;
  234. }
  235. return EFI_SUCCESS;
  236. }
  237. STATIC
  238. EFI_STATUS
  239. FileBufferHide (
  240. VOID
  241. )
  242. {
  243. UINTN i;
  244. for (i = TEXT_START_ROW; i < FileBuffer.MaxVisibleRows; i++ ) {
  245. FileBufferClearLine(i);
  246. }
  247. return EFI_SUCCESS;
  248. }
  249. STATIC
  250. EFI_STATUS
  251. FileBufferClearLine (
  252. UINTN Line
  253. )
  254. {
  255. PrintAt(0,Line,BlankLine);
  256. return EFI_SUCCESS;
  257. }
  258. STATIC
  259. EFI_STATUS
  260. FileBufferSetPosition (
  261. IN UINTN Row,
  262. IN UINTN Column
  263. )
  264. {
  265. FileBuffer.DisplayPosition.Row = Row;
  266. FileBuffer.DisplayPosition.Column = Column;
  267. return EFI_SUCCESS;
  268. }
  269. STATIC
  270. EFI_STATUS
  271. FileBufferRestorePosition (
  272. VOID
  273. )
  274. {
  275. Out->SetCursorPosition (Out,FileBuffer.DisplayPosition.Column,FileBuffer.DisplayPosition.Row);
  276. return EFI_SUCCESS;
  277. }
  278. STATIC
  279. EFI_STATUS
  280. FileBufferScrollDown (
  281. VOID
  282. )
  283. {
  284. UINTN CurrentRow;
  285. UINTN CurrentCol;
  286. UINTN MaxRows;
  287. UINTN HighRow;
  288. EFI_EDITOR_LINE *Line;
  289. BOOLEAN Refresh = FALSE;
  290. Line = LineCurrent();
  291. if (Line->Link.Flink == MainEditor.FileImage->ListHead) {
  292. return EFI_SUCCESS;
  293. }
  294. CurrentRow = FileBuffer.DisplayPosition.Row;
  295. CurrentCol = FileBuffer.DisplayPosition.Column;
  296. MaxRows = FileBuffer.MaxVisibleRows;
  297. HighRow = FileBuffer.HighVisibleRange.Row;
  298. /* Current row is the bottom row, shift only one line, not scroll the whole screen. */
  299. if (CurrentRow == MaxRows) {
  300. FileBuffer.LowVisibleRange.Row += 1;
  301. FileBuffer.HighVisibleRange.Row += 1;
  302. CurrentRow = MaxRows;
  303. Refresh = TRUE;
  304. } else if (CurrentRow == HighRow) {
  305. return EFI_SUCCESS;
  306. } else {
  307. ++CurrentRow;
  308. }
  309. Line = LineNext();
  310. if (FileBuffer.FilePosition.Column > (Line->Size-1)) {
  311. FileBuffer.FilePosition.Column = Line->Size;
  312. if (Line->Size < FileBuffer.LowVisibleRange.Column) {
  313. if (FileBuffer.LowVisibleRange.Column < FileBuffer.MaxVisibleColumns) {
  314. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  315. } else {
  316. FileBuffer.LowVisibleRange.Column = Line->Size - FileBuffer.MaxVisibleColumns + 2;
  317. }
  318. FileBuffer.HighVisibleRange.Column = FileBuffer.LowVisibleRange.Column + FileBuffer.MaxVisibleColumns - 1;
  319. Refresh = TRUE;
  320. }
  321. CurrentCol = FileBuffer.FilePosition.Column - FileBuffer.LowVisibleRange.Column - 1;
  322. }
  323. if (Refresh) {
  324. FileBufferRefresh();
  325. }
  326. FileBuffer.SetPosition(CurrentRow,CurrentCol);
  327. ++FileBuffer.FilePosition.Row;
  328. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  329. return EFI_SUCCESS;
  330. }
  331. STATIC
  332. EFI_STATUS
  333. FileBufferScrollUp (
  334. VOID
  335. )
  336. {
  337. UINTN CurrentRow;
  338. UINTN CurrentCol;
  339. UINTN MaxRows;
  340. UINTN LowRow;
  341. EFI_EDITOR_LINE *Line;
  342. if ( FileBuffer.FilePosition.Row <= TEXT_START_ROW ) {
  343. return EFI_SUCCESS;
  344. }
  345. MaxRows = FileBuffer.MaxVisibleRows;
  346. LowRow = FileBuffer.LowVisibleRange.Row;
  347. CurrentRow = FileBuffer.DisplayPosition.Row;
  348. CurrentCol = FileBuffer.DisplayPosition.Column;
  349. /* Current row is the top row, shift only one line, not scroll the whole screen. */
  350. if (CurrentRow == TEXT_START_ROW) {
  351. FileBuffer.HighVisibleRange.Row -= 1;
  352. FileBuffer.LowVisibleRange.Row -= 1;
  353. CurrentRow = TEXT_START_ROW;
  354. FileBuffer.Refresh();
  355. } else {
  356. CurrentRow--;
  357. }
  358. Line = LinePrevious ();
  359. if (FileBuffer.FilePosition.Column > (Line->Size-1)) {
  360. FileBuffer.FilePosition.Column = Line->Size;
  361. if (Line->Size < FileBuffer.LowVisibleRange.Column) {
  362. if ( FileBuffer.LowVisibleRange.Column < FileBuffer.MaxVisibleColumns ) {
  363. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  364. } else {
  365. FileBuffer.LowVisibleRange.Column = Line->Size - FileBuffer.MaxVisibleColumns + 2;
  366. }
  367. FileBuffer.HighVisibleRange.Column = FileBuffer.LowVisibleRange.Column + FileBuffer.MaxVisibleColumns - 1;
  368. FileBuffer.Refresh();
  369. }
  370. CurrentCol = FileBuffer.FilePosition.Column - FileBuffer.LowVisibleRange.Column - 1;
  371. }
  372. FileBuffer.SetPosition(CurrentRow,CurrentCol);
  373. --FileBuffer.FilePosition.Row;
  374. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  375. return EFI_SUCCESS;
  376. }
  377. STATIC
  378. EFI_STATUS
  379. FileBufferPageUp (
  380. VOID
  381. )
  382. {
  383. UINTN MaxRows;
  384. UINTN LowRow;
  385. UINTN FilePos;
  386. EFI_EDITOR_LINE *Line;
  387. if ( FileBuffer.FilePosition.Row <= TEXT_START_ROW ) {
  388. return EFI_SUCCESS;
  389. }
  390. MaxRows = FileBuffer.MaxVisibleRows;
  391. LowRow = FileBuffer.LowVisibleRange.Row;
  392. FilePos = FileBuffer.FilePosition.Row;
  393. if (LowRow < MaxRows) {
  394. FileBuffer.HighVisibleRange.Row = MaxRows;
  395. FileBuffer.LowVisibleRange.Row = 1;
  396. if (LowRow > TEXT_START_ROW) {
  397. if (FilePos > MaxRows){
  398. FileBuffer.DisplayPosition.Row = FilePos - MaxRows;
  399. } else {
  400. FileBuffer.DisplayPosition.Row = 1;
  401. }
  402. } else {
  403. FileBuffer.DisplayPosition.Row = 1;
  404. FileBuffer.DisplayPosition.Column = TEXT_START_COLUMN;
  405. }
  406. FileBuffer.FilePosition.Row = FileBuffer.DisplayPosition.Row;
  407. } else {
  408. FileBuffer.HighVisibleRange.Row = LowRow;
  409. FileBuffer.LowVisibleRange.Row -= (MaxRows - 1);
  410. FileBuffer.FilePosition.Row -= (MaxRows - 1);
  411. }
  412. LineRetreat(FilePos - FileBuffer.FilePosition.Row);
  413. Line = LineCurrent ();
  414. if (FileBuffer.FilePosition.Column > (Line->Size-1)) {
  415. FileBuffer.FilePosition.Column = Line->Size;
  416. if (Line->Size < FileBuffer.LowVisibleRange.Column ) {
  417. if ( FileBuffer.LowVisibleRange.Column < FileBuffer.MaxVisibleColumns ) {
  418. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  419. } else {
  420. FileBuffer.LowVisibleRange.Column = Line->Size - FileBuffer.MaxVisibleColumns + 2;
  421. }
  422. FileBuffer.HighVisibleRange.Column = FileBuffer.LowVisibleRange.Column + FileBuffer.MaxVisibleColumns - 1;
  423. }
  424. FileBuffer.DisplayPosition.Column = FileBuffer.FilePosition.Column - FileBuffer.LowVisibleRange.Column - 1;
  425. FileBuffer.Refresh();
  426. }
  427. FileBuffer.Refresh();
  428. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  429. return EFI_SUCCESS;
  430. }
  431. STATIC
  432. EFI_STATUS
  433. FileBufferPageDown (
  434. VOID
  435. )
  436. {
  437. UINTN MaxRows;
  438. UINTN HighRow;
  439. UINTN FilePos;
  440. EFI_EDITOR_LINE *Line;
  441. BOOLEAN Refresh = FALSE;
  442. if (FileBuffer.FilePosition.Row == MainEditor.FileImage->NumLines) {
  443. return EFI_SUCCESS;
  444. }
  445. MaxRows = FileBuffer.MaxVisibleRows;
  446. HighRow = FileBuffer.HighVisibleRange.Row;
  447. FilePos = FileBuffer.FilePosition.Row;
  448. FileBuffer.FilePosition.Row = min((FileBuffer.FilePosition.Row+MaxRows-1),MainEditor.FileImage->NumLines);
  449. if (HighRow < MainEditor.FileImage->NumLines) {
  450. FileBuffer.LowVisibleRange.Row = HighRow;
  451. FileBuffer.HighVisibleRange.Row = HighRow + (MaxRows-1);
  452. Refresh = TRUE;
  453. }
  454. FileBuffer.DisplayPosition.Row = TEXT_START_ROW + FileBuffer.FilePosition.Row - FileBuffer.LowVisibleRange.Row;
  455. Line = LineAdvance(FileBuffer.FilePosition.Row - FilePos);
  456. if (FileBuffer.FilePosition.Column > (Line->Size-1) || !Refresh) {
  457. FileBuffer.FilePosition.Column = Line->Size;
  458. if (Line->Size < FileBuffer.LowVisibleRange.Column ) {
  459. if (FileBuffer.LowVisibleRange.Column < FileBuffer.MaxVisibleColumns) {
  460. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  461. } else {
  462. FileBuffer.LowVisibleRange.Column = Line->Size - FileBuffer.MaxVisibleColumns + 2;
  463. }
  464. FileBuffer.HighVisibleRange.Column = FileBuffer.LowVisibleRange.Column + FileBuffer.MaxVisibleColumns - 1;
  465. Refresh = TRUE;
  466. }
  467. FileBuffer.DisplayPosition.Column = FileBuffer.FilePosition.Column - FileBuffer.LowVisibleRange.Column - 1;
  468. }
  469. if (Refresh) {
  470. FileBuffer.Refresh();
  471. }
  472. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  473. return EFI_SUCCESS;
  474. }
  475. STATIC
  476. EFI_STATUS
  477. FileBufferScrollLeft (
  478. VOID
  479. )
  480. {
  481. UINTN CurrentCol;
  482. UINTN CurrentRow;
  483. UINTN MaxCols;
  484. UINTN HighCol;
  485. UINTN LowCol;
  486. EFI_EDITOR_POSITION FilePos;
  487. EFI_EDITOR_LINE *Line;
  488. CurrentCol = FileBuffer.DisplayPosition.Column;
  489. CurrentRow = FileBuffer.DisplayPosition.Row;
  490. MaxCols = FileBuffer.MaxVisibleColumns;
  491. HighCol = FileBuffer.HighVisibleRange.Column;
  492. LowCol = FileBuffer.LowVisibleRange.Column;
  493. FilePos = FileBuffer.FilePosition;
  494. Line = LineCurrent ();
  495. if ( FilePos.Row == 1 && FilePos.Column == 1) {
  496. return EFI_SUCCESS;
  497. }
  498. if ( Line->Size == 0 || FilePos.Column == TEXT_START_COLUMN + 1 ) {
  499. FileBufferScrollUp ();
  500. Line = LineCurrent ();
  501. CurrentCol = Line->Size - 1;
  502. if ( CurrentCol > HighCol ) {
  503. if ( CurrentCol < MaxCols ) {
  504. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  505. FileBuffer.HighVisibleRange.Column = MaxCols;
  506. } else {
  507. FileBuffer.HighVisibleRange.Column = CurrentCol;
  508. FileBuffer.LowVisibleRange.Column = CurrentCol - MaxCols + 1;
  509. }
  510. FileBuffer.Refresh();
  511. }
  512. FileBuffer.FilePosition.Column = CurrentCol + 1;
  513. FileBuffer.DisplayPosition.Column = CurrentCol - FileBuffer.LowVisibleRange.Column;
  514. } else if ( FilePos.Column <= LowCol+1 ) {
  515. if ( LowCol <= MaxCols ) {
  516. LowCol = TEXT_START_COLUMN;
  517. } else {
  518. LowCol -= (MaxCols-1);
  519. }
  520. FileBuffer.LowVisibleRange.Column = LowCol;
  521. FileBuffer.HighVisibleRange.Column = LowCol + MaxCols - 1;
  522. FileBuffer.DisplayPosition.Column = FilePos.Column - LowCol - 2;
  523. --FileBuffer.FilePosition.Column;
  524. FileBuffer.Refresh();
  525. } else {
  526. --FileBuffer.DisplayPosition.Column;
  527. --FileBuffer.FilePosition.Column;
  528. }
  529. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  530. return EFI_SUCCESS;
  531. }
  532. STATIC
  533. EFI_STATUS
  534. FileBufferScrollRight (
  535. VOID
  536. )
  537. {
  538. EFI_EDITOR_POSITION FilePos;
  539. EFI_EDITOR_POSITION CurrentPos;
  540. EFI_EDITOR_LINE *Line;
  541. UINTN LineSize;
  542. UINTN MaxCols;
  543. UINTN LowCol;
  544. UINTN HighCol;
  545. CurrentPos = FileBuffer.DisplayPosition;
  546. FilePos = FileBuffer.FilePosition;
  547. Line = LineCurrent ();
  548. LineSize = Line->Size;
  549. MaxCols = FileBuffer.MaxVisibleColumns;
  550. LowCol = FileBuffer.LowVisibleRange.Column;
  551. HighCol = FileBuffer.HighVisibleRange.Column;
  552. if (FilePos.Column >= (Line->Size-1) && FilePos.Row >= MainEditor.FileImage->NumLines) {
  553. return EFI_SUCCESS;
  554. }
  555. if (LineSize == 0 || FilePos.Column >= LineSize) {
  556. FileBufferScrollDown();
  557. CurrentPos.Column = TEXT_START_COLUMN;
  558. if (LowCol > TEXT_START_COLUMN) {
  559. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  560. FileBuffer.HighVisibleRange.Column = MaxCols;
  561. FileBuffer.Refresh ();
  562. }
  563. FileBuffer.FilePosition.Column = 1;
  564. FileBuffer.DisplayPosition.Column = TEXT_START_COLUMN;
  565. } else if (CurrentPos.Column >= (MaxCols - 1)) {
  566. FileBuffer.LowVisibleRange.Column = HighCol - 2;
  567. FileBuffer.HighVisibleRange.Column = HighCol + MaxCols - 2;
  568. ++FileBuffer.FilePosition.Column;
  569. FileBuffer.DisplayPosition.Column = TEXT_START_COLUMN + 2;
  570. FileBuffer.Refresh();
  571. } else {
  572. ++FileBuffer.FilePosition.Column;
  573. ++FileBuffer.DisplayPosition.Column;
  574. }
  575. MainEditor.StatusBar->SetPosition(FileBuffer.FilePosition.Row,FileBuffer.FilePosition.Column);
  576. return EFI_SUCCESS;
  577. }
  578. STATIC
  579. EFI_STATUS
  580. FileBufferHome (
  581. VOID
  582. )
  583. {
  584. FileBuffer.DisplayPosition.Column = TEXT_START_COLUMN;
  585. FileBuffer.FilePosition.Column = TEXT_START_COLUMN + 1;
  586. if (FileBuffer.LowVisibleRange.Column != TEXT_START_COLUMN) {
  587. FileBuffer.LowVisibleRange.Column = TEXT_START_COLUMN;
  588. FileBuffer.HighVisibleRange.Column = FileBuffer.MaxVisibleColumns;
  589. FileBuffer.Refresh ();
  590. }
  591. MainEditor.StatusBar->SetPosition (FileBuffer.FilePosition.Row,TEXT_START_COLUMN+1);
  592. return EFI_SUCCESS;
  593. }
  594. STATIC
  595. EFI_STATUS
  596. FileBufferEnd (
  597. VOID
  598. )
  599. {
  600. EFI_EDITOR_LINE *Line;
  601. Line = LineCurrent ();
  602. FileBuffer.FilePosition.Column = Line->Size;
  603. if (FileBuffer.HighVisibleRange.Column < (Line->Size - 1)) {
  604. FileBuffer.HighVisibleRange.Column = Line->Size - 1;
  605. FileBuffer.LowVisibleRange.Column = Line->Size - FileBuffer.MaxVisibleColumns;
  606. FileBuffer.Refresh();
  607. }
  608. FileBuffer.DisplayPosition.Column = Line->Size - FileBuffer.LowVisibleRange.Column - 1;
  609. MainEditor.StatusBar->SetPosition (FileBuffer.FilePosition.Row,Line->Size);
  610. return EFI_SUCCESS;
  611. }
  612. STATIC
  613. EFI_STATUS
  614. FileBufferDoCharInput (
  615. IN CHAR16 Char
  616. )
  617. {
  618. switch (Char) {
  619. case 0:
  620. break;
  621. case 0x08:
  622. FileBufferDoBackspace();
  623. break;
  624. case 0x0a:
  625. case 0x0d:
  626. FileBufferDoReturn();
  627. break;
  628. default:
  629. {
  630. EFI_EDITOR_LINE *Line;
  631. UINTN FilePos;
  632. Line = LineCurrent ();
  633. if (Line->Link.Flink != MainEditor.FileImage->ListHead) {
  634. FilePos = FileBuffer.FilePosition.Column - 1;
  635. if (FileBuffer.ModeInsert || FilePos >= Line->Size-1) {
  636. StrInsert (&Line->Buffer,Char,FilePos,Line->Size+1);
  637. Line->Size++;
  638. } else {
  639. Line->Buffer[FilePos] = Char;
  640. }
  641. } else {
  642. Line->Buffer[0] = Char;
  643. Line->Size++;
  644. FileImageCreateNode();
  645. }
  646. FileBufferRefreshCurrentLine();
  647. FileBufferScrollRight();
  648. }
  649. if (!MainEditor.FileModified) {
  650. MainEditor.FileModified = TRUE;
  651. MainEditor.TitleBar->Refresh();
  652. }
  653. break;
  654. }
  655. return EFI_SUCCESS;
  656. }
  657. STATIC
  658. EFI_STATUS
  659. FileBufferDoBackspace (
  660. VOID
  661. )
  662. {
  663. EFI_EDITOR_LINE *Line;
  664. EFI_EDITOR_LINE *End;
  665. LIST_ENTRY *Link;
  666. UINTN FileColumn;
  667. FileColumn = FileBuffer.FilePosition.Column - 1;
  668. if (FileColumn == TEXT_START_COLUMN) {
  669. if (FileBuffer.FilePosition.Row == 1) {
  670. return EFI_SUCCESS;
  671. }
  672. FileBufferScrollLeft();
  673. Line = LineCurrent ();
  674. Link = Line->Link.Flink;
  675. End = CR(Link,EFI_EDITOR_LINE,Link,EFI_EDITOR_LINE_LIST);
  676. LineCat(Line,End);
  677. RemoveEntryList(&End->Link);
  678. FreePool(End);
  679. --MainEditor.FileImage->NumLines;
  680. FileBufferRefresh();
  681. } else {
  682. Line = LineCurrent ();
  683. LineDeleteAt(Line,FileColumn-1);
  684. FileBufferRefreshCurrentLine();
  685. FileBufferScrollLeft();
  686. }
  687. if (!MainEditor.FileModified) {
  688. MainEditor.FileModified = TRUE;
  689. MainEditor.TitleBar->Refresh();
  690. }
  691. return EFI_SUCCESS;
  692. }
  693. STATIC
  694. EFI_STATUS
  695. FileBufferDoDelete (
  696. VOID
  697. )
  698. {
  699. EFI_EDITOR_LINE *Line;
  700. EFI_EDITOR_LINE *Next;
  701. LIST_ENTRY *Link;
  702. UINTN FileColumn;
  703. Line = LineCurrent ();
  704. FileColumn = FileBuffer.FilePosition.Column - 1;
  705. if (Line->Link.Flink == MainEditor.FileImage->ListHead) {
  706. return EFI_SUCCESS;
  707. }
  708. if (FileColumn >= Line->Size - 1) {
  709. Link = Line->Link.Flink;
  710. if (Link->Flink == MainEditor.FileImage->ListHead) {
  711. return EFI_SUCCESS;
  712. }
  713. Next = CR(Link,EFI_EDITOR_LINE,Link,EFI_EDITOR_LINE_LIST);
  714. LineCat(Line,Next);
  715. RemoveEntryList(&Next->Link);
  716. FreePool(Next);
  717. --MainEditor.FileImage->NumLines;
  718. FileBufferRefresh();
  719. } else {
  720. LineDeleteAt (Line,FileColumn);
  721. FileBufferRefreshCurrentLine();
  722. }
  723. if (!MainEditor.FileModified) {
  724. MainEditor.FileModified = TRUE;
  725. MainEditor.TitleBar->Refresh();
  726. }
  727. return EFI_SUCCESS;
  728. }
  729. STATIC
  730. EFI_STATUS
  731. FileBufferDoReturn (
  732. VOID
  733. )
  734. {
  735. EFI_EDITOR_LINE *Line;
  736. EFI_EDITOR_LINE *NewLine;
  737. UINTN FileColumn;
  738. Line = LineCurrent ();
  739. FileColumn = FileBuffer.FilePosition.Column - 1;
  740. NewLine = AllocatePool(sizeof(EFI_EDITOR_LINE));
  741. NewLine->Signature = EFI_EDITOR_LINE_LIST;
  742. NewLine->Size = Line->Size - FileColumn;
  743. if (NewLine->Size > 1) {
  744. NewLine->Buffer = PoolPrint(L"%s\0",Line->Buffer+FileColumn);
  745. } else {
  746. NewLine->Buffer = PoolPrint(L" \0");
  747. }
  748. Line->Buffer[FileColumn] = ' ';
  749. Line->Buffer[FileColumn+1] = 0;
  750. Line->Size = FileColumn + 1;
  751. NewLine->Link.Blink = &(Line->Link);
  752. NewLine->Link.Flink = Line->Link.Flink;
  753. Line->Link.Flink->Blink = &(NewLine->Link);
  754. Line->Link.Flink = &(NewLine->Link);
  755. ++MainEditor.FileImage->NumLines;
  756. BS->Stall(50);
  757. FileBufferRefreshDown();
  758. FileBufferScrollRight();
  759. if (!MainEditor.FileModified) {
  760. MainEditor.FileModified = TRUE;
  761. MainEditor.TitleBar->Refresh();
  762. }
  763. return EFI_SUCCESS;
  764. }
  765. STATIC
  766. EFI_STATUS
  767. FileBufferChangeMode (
  768. VOID
  769. )
  770. {
  771. FileBuffer.ModeInsert = !FileBuffer.ModeInsert;
  772. MainEditor.StatusBar->SetMode(FileBuffer.ModeInsert);
  773. MainEditor.StatusBar->Refresh();
  774. return EFI_SUCCESS;
  775. }
  776. #endif /* _LIB_FILE_BUFFER */