Simple Word Wrap procedure

bbc micro/electron/atom/risc os coding queries and routines
Post Reply
vela025
Posts: 198
Joined: Tue Jun 16, 2020 4:48 pm
Contact:

Simple Word Wrap procedure

Post by vela025 »

Hi all,

I'm creating a simple text editor script (please be kind :lol: ) that can do text wrapping for messages. I've made some progress (although it is far for an elegant solution). My thought process was to store each line (40 characters) in an array. So that the text can be read in either 40 or 80 columns by either displaying one or two arrays next to each other. (i.e. PRINT b$(X$) or PRINT b$(X%)+" "+b$(X%+1).

I have the wrap portion working...however if backspace is pressed on the preceeding line then it all goes wrong. I've tried fixing this a few different ways but can't get it quite right and my brain is now a bit fried.

I'm looking for a few pointers on how to fix the backsapce issue so that it will delete the previous character (without spliting subsequent lines) or if the cursor position is the start of a line will return the cursor position to the end of the previous line for editing.

Code: Select all

  120 M$=""
  130 b$(X%)=""
  131 S%=0
  140 REPEAT
  150 a$=INKEY$(3000)
  160 IF a$="" VDU7:PROCstatus(" INACTIVITY WARNING"):a$=INKEY$(1000)
  170 IF a$="" THEN PROCdc
  181 IF a$=CHR$13 THEN PRINT ';:a$=INKEY$(3000):IF a$="/" THEN PRINT a$:PROCco
  182 IF a$=CHR$13 THEN PRINT ';
  190 IF ASC(a$) <> 8 THEN M$=M$+a$
  200 IF ASC(a$) = 8 THEN PROCbk
  210 IF LEN (a$)>0 THEN PRINT a$;
  240 IF LEN(M$)=40 THEN b$(X%)=M$:Y%=X%:X%=X%+1:M$="":IF RIGHT$(b$(Y%),1)<>CHR$20 THEN PROCwrap
  241 IF a$=CHR$13 THEN b$(X%)=M$:X%=X%+1:a$="":M$=""
  260 UNTIL X%=41 OR EMSG%=TRUE
  270 END
  280 DEFPROCwrap
  290 REPEAT:S%=S%+1:sp$=LEFT$(RIGHT$(b$(Y%),S%),1):UNTIL sp$=" ":M$=RIGHT$(b$(Y%),(S%-1)):b$(Y%)=LEFT$(b$(Y%),(40-S%)):VDU11:VDU13:PRINT b$(Y%);:FOR I%=1 TO (40-LEN(b$(Y%))):PRINT" ";:NEXT I%:S%=0:PRINT M$;:L%=41
  300 ENDPROC
  310 DEFPROCco
  320 a$=INKEY$(3000):PRINT a$;
  330 IF a$ = "S" THEN PRINT "SAVED":EMSG%=TRUE
  340 ENDPROC
  350 DEFPROCbk
  360 IF ASC(a$) = 8 AND LEN(M$)>0 THEN M$=LEFT$(M$,(LEN(M$)-1)):ENDPROC
  370 IF ASC(a$) = 8 AND LEN(M$)=0 THENVDU11:VDU13:X%=X%-1:M$=RIGHT$(b$(X%),39)
  380 ENDPROC
  
BBC Master 128, PiTubeDirect, RGB2HDMI, Twin 5 1/4" & GoTek, BeebSCSI, Retroclinic Datacentre (E), Oki Microline 280, Sony TCM-737, Miracle WS2000 Modem, WE Mouse. BeeBS BBS - http://beebs.ddns.net
User avatar
geraldholdsworth
Posts: 1401
Joined: Tue Nov 04, 2014 9:42 pm
Location: Inverness, Scotland
Contact:

Re: Simple Word Wrap procedure

Post by geraldholdsworth »

I wrote something similar, but in Pascal:

Code: Select all

 procedure WrapText(wtText: String);
 var
  LStart,
  LLength: Integer;
 begin
  //Only wrap if it is longer than the available width
  if(FTextWrap)and(FContent.Canvas.TextWidth(wtText)+XPos>W)then
  begin
   //Start at the beginning
   LStart:=1;
   //And continue until we are out of characters
   while LStart<Length(wtText) do
   begin
    //Length of remaining string (if LStart+LLength are bigger than the string
    //length, then it'll just go to the end of the string)
    LLength:=Length(wtText);
    //Reduce the length until it'll fit
    while(FContent.Canvas.TextWidth(Copy(wtText,LStart,LLength))+XPos>W)
      and(LLength>1)do dec(LLength);
    //Then print what we can
    PrintText(Copy(wtText,LStart,LLength));
    //And move the starting position along
    inc(LStart,LLength);
    //If there are more characters left, then do a CR and LF
    if LStart<=Length(wtText) then
    begin
     //Move the Y pointer downwards
     inc(YPos,FContent.Canvas.TextHeight(wtText)+FLineSpace);
     //Reset X pointer
     XPos:=FLineSpace;
    end;
   end;
   //The string is only a single character, but still won't fit, so CR LF
   if Length(wtText)=1 then
   begin
    //Move the Y pointer downwards
    inc(YPos,FContent.Canvas.TextHeight(wtText)+FLineSpace);
    //Reset X pointer
    XPos:=FLineSpace;
   end;
   //The starting point is the last character, so print and move along
   if LStart=Length(wtText) then PrintText(Copy(wtText,LStart));
  end
  else PrintText(wtText);//No text wrapping
 end;
Difference here is that it goes by width in pixels.
Gerald Holdsworth, CTS-D
Extron Authorised Programmer
https://www.geraldholdsworth.co.uk
https://www.reptonresourcepage.co.uk
Twitter @radiogezza
User avatar
jgharston
Posts: 5321
Joined: Thu Sep 24, 2009 12:22 pm
Location: Whitby/Sheffield
Contact:

Re: Simple Word Wrap procedure

Post by jgharston »

I have a variant that wordwraps centred text!

Code: Select all

  590 DEFPROCc(A$,W%):A$=A$+" ":REPEAT
  600   A%=W%+1:REPEAT:A%=A%-1:UNTIL MID$(A$,A%,1)=" " OR A%<0:IF A%<0:A%=W%+1
  610   PRINT STRING$(W%DIV2-A%DIV2,CHR$9);LEFT$(A$,A%-1);:IF A%>W%:VDU 8:A%=A%-1
  620   A$=MID$(A$,A%+1):IF A$<>"":PRINT
  630 UNTIL A$="":ENDPROC
Try, eg: PROCc("The quick brown fox jumps over the lazy dog",15)

Code: Select all

$ bbcbasic
PDP11 BBC BASIC IV Version 0.45
(C) Copyright J.G.Harston 1989,2005-2024
>_
vela025
Posts: 198
Joined: Tue Jun 16, 2020 4:48 pm
Contact:

Re: Simple Word Wrap procedure

Post by vela025 »

Hey both, thanks for the replies...I sussed it in the end (amungst other issues I discovered along the way) I was using CHR$8 to detect the backspace key being pressed....rather than 127 (getting confused with VDU8). #-o
BBC Master 128, PiTubeDirect, RGB2HDMI, Twin 5 1/4" & GoTek, BeebSCSI, Retroclinic Datacentre (E), Oki Microline 280, Sony TCM-737, Miracle WS2000 Modem, WE Mouse. BeeBS BBS - http://beebs.ddns.net
Post Reply

Return to “programming”