/* Copyright 1996 Acorn Computers Ltd * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /* * Title: txt.c * Purpose: Text display object. * Author: WRS * History: * 16 July 87 -- started * 30-Nov-87: WRS: converted into C. * 02-Mar-88: WRS: convertion complete. * 08-May-91: ECN: #ifndefed out unused ROM functions */ #define BOOL int #define TRUE 1 #define FALSE 0 #include <stdlib.h> #include <stdarg.h> #include "h.txt" #include "h.EditIntern.txtundo" #include "h.EditIntern.txt1" #include "h.EditIntern.txt3" #include "h.EditIntern.txtar" #include "h.werr" #include "h.trace" /* The type txt__str is actually provided by module txt1 */ /* ----------------------------------------------------- */ /* Module Structure of text implementation: ======================================= There are three key modules. There are recursive dependencies so that the Texts module itself does not betray its implementation. txt: does the lock grabbing (if necessary), then calls txt1 (buffer manipulation) or procedures installed by the window implementation (probably txt2). System-independent, uncontrovertial. h.txt is the only public part of this whole thing. txt1: the horrid but system-independent buffer manipulation and display calls. h.txt1 also has the main internal data structures declared. calls window procedures for system-dependent display primitives. txt2: the system-dependent stuff, installs window procedures in the text object. Other implementations are possible. Calls txt1 for editing operations provoked by user events. */ txt txt_new(char *title) { txt t; t = malloc(sizeof(txt1_str)); if (t == 0) { tracef0("txt_new fails.\n"); return 0; }; t->oaction = txt_EXTEND; t->charoptionset = txt_DISPLAY + txt_CARET; if (! txt1_inittextbuffer(t)) { free(t); return 0; }; t->inbufhead = 0; t->inbuftail = 0; t->eventproc = (txt_event_proc) 0; t->eventprochandle = 0; t->eventnest = 0; t->disposepending = FALSE; txt3_inittxt(t); /* cannot fail. */ if (! txtar_initwindow(t, title)) { txt1_disposetextbuffer(t); free(t); return 0; }; t->undostate = txtundo_new(); if (t->undostate == 0) { txt3_disposeallwindows(t); txt1_disposetextbuffer(t); free(t); return 0; }; return t; } void txt_show(txt t) { while (txt3_foreachwindow(t)) { t->w->doshow(t); } } void txt_hide(txt t) { while (txt3_foreachwindow(t)) { t->w->dohide(t); } } void txt_settitle(txt t, char* title) { while (txt3_foreachwindow(t)) { t->w->dosettitle(t, title); } } void txt_dispose(txt *t) { if ((*t)->eventnest == 0) { txt1_disposetextbuffer(*t); txt3_disposeallwindows(*t); txtundo_dispose(&((*t)->undostate)); free(*t); } else { (*t)->disposepending = TRUE; }; } /* -------- General control operations. -------- */ #ifndef UROM int txt_bufsize(txt t) { return txt1_dobufsize(t); } #endif #ifndef UROM BOOL txt_setbufsize(txt t, int size) { return txt1_dosetbufsize(t, size); } #endif #if FALSE txt_overflowaction txt_oaction(txt t) { return txt1_dooaction(t); } void txt_setoaction(txt t, txt_overflowaction o) { txt1_dosetoaction(t, o); } #endif txt_charoption txt_charoptions(txt t) { return t->charoptionset; } void txt_setcharoptions(txt t, txt_charoption affect, txt_charoption values) { txt1_dosetcharoptions(t, affect, values); } void txt_setdisplayok(txt t) { txt1_dosetdisplayok(t); } int txt_lastref(txt t) { return t->last_ref; } void txt_setlastref(txt t, int newvalue) { t->last_ref = newvalue; } /* -------- Operations on the array of characters. -------- */ txt_index txt_dot(txt t) { return txt1_dodot(t); } txt_index txt_size(txt t) /* max value that dot can take */ { return txt1_dosize(t); } void txt_setdot(txt t, txt_index i) { txt1_dosetdot(t, i); } void txt_movedot(txt t, int by) { txt1_domovedot(t, by); } void txt_insertchar(txt t, char c) { txt1_doinsertchar(t, c); } void txt_insertstring(txt t, char* s) { txt1_doinsertstring(t, s); } void txt_delete(txt t, int n) { txt1_dodelete(t, n); } void txt_replacechars(txt t, int ntodelete, char* chars, int n) { txt1_doreplacechars(t, ntodelete, chars, n); } char txt_charatdot(txt t) { return txt1_docharatdot(t); } char txt_charat(txt t, txt_index i) { return txt1_docharat(t, i); } #ifndef UROM void txt_charsatdot(txt t, char/*out*/ *buffer, int /*inout*/ *n) { txt1_docharsatdot(t, buffer, n); } #endif void txt_replaceatend(txt t, int ntodelete, char *buffer, int n) { txt1_doreplaceatend(t, ntodelete, buffer, n); } /* -------- Layout-dependent Operations. -------- */ void txt_movevertical(txt t, int by, int caretstill) { txt1_domovevertical(t, by, caretstill); } void txt_movehorizontal(txt t, int by) { txt1_domovehorizontal(t, by); } int txt_visiblelinecount(txt t) { return t->w->dovisiblelinecount(t); } #ifndef UROM int txt_visiblecolcount(txt t) { return t->w->dovisiblecolcount(t); } #endif /* -------- Operations on Markers. -------- */ void txt_newmarker(txt t, txt_marker* m) { txt1_donewmarker(t, (txt1_imarker*) m); } void txt_movemarker(txt t, txt_marker* m, txt_index to) { txt1_domovemarker(t, (txt1_imarker*) m, to); } void txt_movedottomarker(txt t, txt_marker* m) { txt1_domovedottomarker(t, (txt1_imarker*) m); } txt_index txt_indexofmarker(txt t, txt_marker* m) { return txt1_doindexofmarker(t, (txt1_imarker*) m); } void txt_disposemarker(txt t, txt_marker* m) { txt1_dodisposemarker(t, (txt1_imarker*) m); } /* -------- Operations on the selection. -------- */ BOOL txt_selectset(txt t) { return txt1_doselectset(t); } txt_index txt_selectstart(txt t) { return txt1_doselectstart(t); } txt_index txt_selectend(txt t) { return txt1_doselectend(t); } void txt_setselect(txt t, txt_index start, txt_index end) { txt1_dosetselect(t, start, end); } /* -------- Input from the user -------- */ txt_eventcode txt_get(txt t) { return t->w->doget(t); } #ifndef UROM int txt_queue(txt t) { return t->w->doqueue(t); } #endif void txt_unget(txt t, txt_eventcode code) { t->w->dounget(t, code); } void txt_eventhandler(txt t, txt_event_proc e, void* handle) { t->eventproc = e; t->eventprochandle = handle; } void txt_readeventhandler(txt t, txt_event_proc *proc, void **handle) { *proc = t->eventproc; *handle = t->eventprochandle; } /* -------- Direct Access to the array of characters. -------- */ void txt_arrayseg(txt t, txt_index at, char **a, int *n) { txt1_doarraysegment(t, at, a, n); } /* -------- System hook. -------- */ int txt_syshandle(txt t) { return t->w->dosyshandle(t); } void txt_init(void) { return; /* @@@ Do nothing for the moment (maybe one day) */ } /* -------- STUBS FOR M2. -------- */ #if FALSE /* -------- Modula-2 equivalents. -------- */ txt Texts_New(char *title); void Texts_Show(txt t); void Texts_Hide(txt t); void Texts_SetTitle(txt t, char* title); void Texts_Dispose(txt *t); /* -------- General control operations. -------- */ int Texts_BufSize(txt t); int Texts_SetBufSize(txt t, int s); txt_overflowaction Texts_OAction(txt); void Texts_SetOAction(txt t, txt_overflowaction); txt_charoption Texts_CharOptions(txt); void Texts_SetCharOptions(txt t, txt_charoption affect, txt_charoption values); /* -------- Operations on the array of characters. -------- */ txt_index Texts_Dot(txt); txt_index Texts_Size(txt); /* max value that dot can take */ void Texts_SetDot(txt t, txt_index); void Texts_MoveDot(txt t, int by); void Texts_InsertChar(txt t, char); void Texts_InsertString(txt t, char*); void Texts_Delete(txt t, int); void Texts_ReplaceChars(txt t, int ntodelete, char*, int n); char Texts_CharAtDot(txt); char Texts_CharAt(txt t, txt_index); void Texts_CharsAtDot(txt t, char*/*out*/ buffer, int* /*inout*/ n); /* -------- Layout-dependent Operations. -------- */ void Texts_MoveVertical(txt t, int by, int caretstill); void Texts_MoveHorizontal(txt t, int by); int Texts_VisibleLineCount(txt); int Texts_VisibleColCount(txt); /* -------- Operations on Markers. -------- */ void Texts_NewMarker(txt t, txt_marker*); void Texts_MoveMarker(txt t, txt_marker*, txt_index to); void Texts_MoveDotToMarker(txt t, txt_marker*); txt_index Texts_IndexOfMarker(txt t, txt_marker*); void Texts_DisposeMarker(txt t, txt_marker*); /* -------- Operations on the selection. -------- */ int Texts_SelectSet(txt); /* returns 1 or 0 */ txt_index Texts_SelectStart(txt); txt_index Texts_SelectEnd(txt); void Texts_SetSelect(txt t, txt_index start, txt_index end); /* -------- Input from the user -------- */ txt_eventcode Texts_Get(txt); int Texts_Queue(txt); void Texts_EventHandler(txt t, void(e)(txt,void*), void*); /* -------- Direct Access to the array of characters. -------- */ void Texts_ArraySegment(txt t, txt_index at, char **a, int *n); /* -------- System hook. -------- */ int Texts_SysHandle(txt); /* end */ /*************************************/ txt txt_new(char *title) { return(Texts_New(title)); } void txt_show(txt t) { Texts_Show(t); } void txt_hide(txt t) { Texts_Hide(t); } void txt_settitle(txt t, char* title) { Texts_SetTitle(t, title); } void txt_dispose(txt *t) { Texts_Dispose(t); } /* -------- General control operations. -------- */ int txt_bufsize(txt t) { return Texts_BufSize(t); } int txt_setbufsize(txt t, int size) { return Texts_SetBufSize(t, size); } txt_overflowaction txt_oaction(txt t) { return Texts_OAction(t); } void txt_setoaction(txt t, txt_overflowaction o) { Texts_SetOAction(t, o); } txt_charoption txt_charoptions(txt t) { return Texts_CharOptions(t); } void txt_setcharoptions(txt t, txt_charoption affect, txt_charoption values) { Texts_SetCharOptions(t, affect, values); } /* -------- Operations on the array of characters. -------- */ txt_index txt_dot(txt t) { return Texts_Dot(t); } txt_index txt_size(txt t) /* max value that dot can take */ { return Texts_Size(t); } void txt_setdot(txt t, txt_index i) { Texts_SetDot(t, i); } void txt_movedot(txt t, int by) { Texts_MoveDot(t, by); } void txt_insertchar(txt t, char c) { Texts_InsertChar(t, c); } void txt_insertstring(txt t, char* s) { Texts_InsertString(t, s); } void txt_delete(txt t, int n) { Texts_Delete(t, n); } void txt_replacechars(txt t, int ntodelete, char* chars, int n) { Texts_ReplaceChars(t, ntodelete, chars, n); } char txt_charatdot(txt t) { return Texts_CharAtDot(t); } char txt_charat(txt t, txt_index i) { return Texts_CharAt(t, i); } void txt_charsatdot(txt t, char/*out*/ *buffer, int /*inout*/ *n) { Texts_CharsAtDot(t, buffer, n); } /* -------- Layout-dependent Operations. -------- */ void txt_movevertical(txt t, int by, int caretstill) { Texts_MoveVertical(t, by, caretstill); } void txt_movehorizontal(txt t, int by) { Texts_MoveHorizontal(t, by); } int txt_visiblelinecount(txt t) { return Texts_VisibleLineCount(t); } int txt_visiblecolcount(txt t) { return Texts_VisibleColCount(t); } /* -------- Operations on Markers. -------- */ void txt_newmarker(txt t, txt_marker* m) { Texts_NewMarker(t, m); } void txt_movemarker(txt t, txt_marker* m, txt_index to) { Texts_MoveMarker(t, m, to); } void txt_movedottomarker(txt t, txt_marker* m) { Texts_MoveDotToMarker(t, m); } txt_index txt_indexofmarker(txt t, txt_marker* m) { return Texts_IndexOfMarker(t, m); } void txt_disposemarker(txt t, txt_marker* m) { Texts_DisposeMarker(t, m); } /* -------- Operations on the selection. -------- */ int txt_selectset(txt t) /* returns 1 or 0 */ { return Texts_SelectSet(t); } txt_index txt_selectstart(txt t) { return Texts_SelectStart(t); } txt_index txt_selectend(txt t) { return Texts_SelectEnd(t); } void txt_setselect(txt t, txt_index start, txt_index end) { Texts_SetSelect(t, start, end); } /* -------- Input from the user -------- */ txt_eventcode txt_get(txt t) { return Texts_Get(t); } int txt_queue(txt t) { return Texts_Queue(t); } void txt_eventhandler(txt t, void(e)(txt,void*), void* handle) { Texts_EventHandler(t, e, handle); } /* -------- Direct Access to the array of characters. -------- */ void txt_arrayseg(txt t, txt_index at, char **a, int *n) { Texts_ArraySegment(t, at, a, n); } /* -------- System hook. -------- */ int txt_syshandle(txt t) { return Texts_SysHandle(t); } #endif /* end */