Giter VIP home page Giter VIP logo

owlet-editor's Introduction

Owlet Editor🦉 Owlet CI and CD

A simple, intuitive creative coding tool for BBC BASIC inspired by BBC Micro Bot

Try the beta now at bbcmic.ro and get coding!

A modern editor for a classic language

  • Fast, intuitive web-based editor (autocomplete, highlighting)
  • Linked to 1000 BBC BASIC code examples from the bbcmicrobot community
  • Based on Monaco editor

BBC Micro emulator for instant feedback

  • Integrated with JSbeeb emulator
  • Share your entire program as a URL
  • Export to external emulator for interactive use

Share your creations with the BBC Micro Bot Mastodon community

  • One button tweet to share code (not yet updated for Mastodon)
  • Automatic code golfing tools - byte token encode/decode

To develop

$ make run

then visit http://localhost:8080

owlet-editor's People

Contributors

8bitkick avatar mattgodbolt avatar ojwb avatar tom-seddon avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

owlet-editor's Issues

Show timing information

A significant feature the old editor had which owlet seems to currently lack is timing information. The bot waits 30 seconds then records for 3 seconds, and in many cases it's really useful to see what happens in those 3 seconds before sending the code to the bot.

Right now to test timing I use a local install of the bot code so I can run node client try and then copy and paste the code from owlet to a terminal, which is all a bit fiddly (especially because you seem to explicitly need to copy and I'm used to X-style select-to-copy). I doubt many users will bother with this.

The old editor's timing didn't entirely match what happened in the bot, but was good enough for many cases.

'

' in a PRINT emits a CR+LF, but the editor colours it red as if it's an error:

P.'"a"'@%''TIME'

"Pretty printer" for BASIC

Expanding out the whole thing from the (sometimes) compressed mass of P."moo";:?A=1:MO.2 into separate lines. Would need to handle line numbering cleverly.

Invalid operators

It would be helpful to people less familiar with BBC BASIC if invalid operators were highlighted in red like many other invalid cases are - especially for cases which are valid in other BASIC dialects and/or other languages. E.g.:

A=1:B=1:C=1:ONERRORREPORT:P." at line ";ERL;:G.ERL+10
A+=B
A-=B
A/=B
A*=B
A^=B
A=B<<C
A=B>>C
IFA==B:P.
IFA!=B:P.
IFA=>B:P.
IFA=<B:P.
IFA><B:P.
END

Some of these even work in later BBC BASIC versions.

(The "backwards" =>, etc are supported by e.g. Apple II BASIC)

"new" button

Having a new button (other than ctrl+a+backspace) would be good - on mobile deleting the whole program there is a pain

Improve tokeniser performance

@8bitkick points out the editor is feeling a little sluggish. A super quick profile shows we're spending a bunch of time in the tokeniser, unsurprisingly probably due to the giant regex we use to tokenise. Most "sensible" languages use whitepsace to terminate tokens, and monaco is optimised for that. We have to disable it though as PRINTLEN is two tokens without whitespace :)

Highlighting of decimal point corner cases

Consider:

P.1.,.5,.

Here .5 is highlighted as a number (good), but in 1. the . is red, and . by itself is also red (but this is really the same as 0.0 as you can see if you run this program). I think 1. and . should both be highlighted as numbers.

TOP

TOP is a bit of an odd-ball keyword in that it doesn't actually have its own token but is actually tokenised as a TO token followed by a letter P.

The syntax highlighting doesn't seem to know about this quirk, e.g. this actually colours the P brown instead of blue:

PRINT TOP

You can't just colour any P after TO blue though, consider:

F.P=TOP TOP:P.P:N.

There the first TOP is TOP, but the second TOP is actually TO P.

display hex placeholders for 0x80-0xFF

cosmetic enhancement: when you shrink code, you see a mess of accented characters and blanks in the editor. A bunch of the byte tokens for keywords fall into the C1 control character block, so just show up as spaces. It makes it hard to tell what's going on (and I know, I'm reading the compressed code - I shouldn't really care)

Making the spans that contain the tokens have title attributes with the expanded keyword would be ideal, since then mouseover would reveal what is going on. However, this doesn't seem possible with monaco. Another solution does work tho:

@font
-face {
 font-family: 'Unprintable';
 src: local('Unicode BMP Fallback SIL');
 unicode-range: U+80-9F,U+A1-FF;
} 

declare a fallback font, 'Unprintable', for the high-byte characters. SIL BMP displays hexadecimal instead of the normal glyphs https://scripts.sil.org/cms/scripts/page.php?site_id=nrsi&id=unicodebmpfallbackfont
... the full font covers all of the basic multilingual plane, subsetting it to just the ones used would be ideal. Here I'm using a local font but the font would have to be imported for most users. A0 is excluded, since I see the editor uses non-breaking spaces to display normal spaces in the code.
Then just use Unprintable as the first font, so it replaces that character range:

.monaco-editor {
    font-family: Unprintable,-apple-system,BlinkMacSystemFont,Segoe WPC,Segoe UI,HelveticaNeue-Light,system-ui,Ubuntu,Droid Sans,sans-serif;
    --monaco-monospace-font: Unprintable,"SF Mono",Monaco,Menlo,Consolas,"Ubuntu Mono","Liberation Mono","DejaVu Sans Mono","Courier New",monospace;
}

"undo" seemingly limited

While playing around and running the code it seems like the "undo" doesn't go back as far as I like. Sometimes only one step. Not sure what's causing this, maybe something is setValue()-ing the code unnecessarily?

Add a "suggested fix" for "H.TO"

See #36 - abbreviated tokens are "MISTAKE"s, but putting a space fixes it. Put wigglies under it instead of just making it red, and then have an action to fix it.

Erroneous ~ not highlighted

Following on from #20...

The current state is better than before the fix for #20, but ~ now seems to be treated as an operator like +, etc but really it's more like ' as it can't be used in most expressions. I think it only works in PRINT and as the next token after STR$ (so A$=STR$~(12) and B$=STR$~12 work, but C$=STR$(~12) doesn't.)

Admittedly a minor issue, but ideally A=~B should show ~ in red.

Torture test for editor

 MODE 2:!-512=720907:$@%="1022":!80=&2030605: DIM S(18),C(18): FOR L=0 TO 18:A= RAD(21*L-9):S(L)= SINA*23:C(L)= COSA*28: NEXT : PRINT "���PRESS CONFERENCE";
 FOR C= FNb(640,-240,9,9) TO 4:C=3 AND C: VDU 31,6- INKEY75;: PRINT  MID$("AUTUMNWINTERSPRINGSUMMER",C*6+1,6): VDU 19,1,@%?C;0;19,2,C?80;0;: NEXT 
 DEF  FNb(X,Y,A,D) IF D MOVE X,Y:U=S(A)*D:V=C(A)*D: VDU 18;1+D/2,281;-U;-V;18;D/2+.5: PLOT 49,U,V:X=X-U:Y=Y-V:= FNb(X,Y,A+ FNb(X,Y,A-1,D-1),D-1)
=1

Lots of issues show up here (wordwrapping; for which "bounded" doesn't work properly even), comments.

Examples issues

In the ‘examples’ tab on the right, the text doesn’t wrap. Presumably because it’s better to maintain a separate ‘this is the first line, this is the second line’ concept… however it did make it a tad painful to select the text when I wanted to copy-paste it into the left-hand editor pane.

"Overclock mode" option

Add support to run in overclocked mode. In jsbeeb as-is it's limited to probably 2.5-3x real speed.

^

^ should get highlighted as an operator, but it's currently red:

F.A=H. TO8^5:?A=42:N.

Don't suggest keywords which are invalid in a program

Some keywords don't work in a program so it's not helpful to suggest them as completions.

It seems the list is AUTO, LIST, RENUMBER, NEW, OLD, LOAD, SAVE but I may have missed some (or contexts where some of those work). (Note CHAIN and RUN are valid in a program.)

ASM example

https://bbcmic.ro/#%7B%22v%22%3A1%2C%22program%22%3A%22DIM%20MC%25%20400%3AFOR%20O%25%3D0%20TO%203%20STEP%203%3AP%25%3DMC%25%3A%5B%3AOPT%20O%25%3A.H%25%20EQUW%20%2655AA%3A.S%25%20EQUW%20%263000%3A.Y%25%20EQUD%20%26FCF0C000%3AEQUD%20%26030F3FFF%3A.g%20LDA%20S%25%3ASTA%20%2670%3ALDA%20S%25%2B1%3ASTA%20%2671%3ALDY%20%230%3A.t%20LDA%20H%25%3ASTA%20(%2670)%2CY%3AINY%3ALDA%20H%25%2B1%3ASTA%20(%2670)%2CY%3AINY%3ABNE%20t%3ALDY%20%230%3AINC%20%2671%3ABPL%20t%3A.c%20LDA%20S%25%3ACLC%5CnADC%20%2332%3ASTA%20%2676%3ALDA%20S%25%2B1%3ASTA%20%2677%3ALDA%20%230%3ASTA%20%2672%3A.a%20ASL%20A%3AAND%20%237%3ASTA%20%2673%3ALDA%20%2676%3ASTA%20%2678%3ALDA%20%2677%3ASTA%20%2679%3ALDA%20%230%3ASTA%20%2674%3A.l%20LDA%20%2678%3ASTA%20%267A%3ALDA%20%2679%3ASTA%20%267B%3ALDA%20%2673%3ACLC%3AADC%20%267C%3AAND%20%23%267%3ATAY%3ALDA%20Y%25%2CY%3ALDY%20%230%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%5CnINY%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%3AINY%3ASTA%20(%267A)%2CY%3ALDA%20%23%26F0%3ABIT%20%2674%3ABNE%20e%3ALDA%20%23%262%3ABIT%20%2672%3ABNE%20k%3AJMP%20f%3A.e%20LDA%20%23%262%3ABIT%20%2672%3ABNE%20f%3AJMP%20k%3A.f%20LDA%20%2673%3ACLC%3AADC%20%231%3AAND%20%237%3ASTA%20%2673%3AJMP%20i%3A.k%20LDA%20%2673%3ACLC%3AADC%20%237%3AAND%20%237%3ASTA%20%2673%3A.i%20CLC%3ALDA%20%2678%3AADC%20%23%2680%3ASTA%20%2678%5CnLDA%20%2679%3AADC%20%232%3ASTA%20%2679%3ALDA%20%2674%3ACLC%3AADC%20%231%3ASTA%20%2674%3ACMP%20%2332%3ABNE%20l%3ALDA%20%2676%3ACLC%3AADC%20%2364%3ASTA%20%2676%3ALDA%20%2677%3AADC%20%230%3ASTA%20%2677%3ALDA%20%2672%3ACLC%3AADC%20%231%3ASTA%20%2672%3ACMP%20%2310%3ABEQ%20r%3AJMP%20a%3A.r%20LDA%20%267C%3ACLC%3AADC%20%23%261%3AAND%20%23%267%3ASTA%20%267C%3AJMP%20c%3ARTS%3A%5D%3ANEXT%3AMODE%200%3AVDU23%2C1%2C0%3B0%3B0%3B0%3B%3A*FX19%5CnCALL%20g%22%7D

Worth a look to get inline asm syntax looking nicely.

DIM MC% 400:FOR O%=0 TO 3 STEP 3:P%=MC%:[:OPT O%:.H% EQUW &55AA:.S% EQUW &3000:.Y% EQUD &FCF0C000:EQUD &030F3FFF:.g LDA S%:STA &70:LDA S%+1:STA &71:LDY #0:.t LDA H%:STA (&70),Y:INY:LDA H%+1:STA (&70),Y:INY:BNE t:LDY #0:INC &71:BPL t:.c LDA S%:CLC
ADC #32:STA &76:LDA S%+1:STA &77:LDA #0:STA &72:.a ASL A:AND #7:STA &73:LDA &76:STA &78:LDA &77:STA &79:LDA #0:STA &74:.l LDA &78:STA &7A:LDA &79:STA &7B:LDA &73:CLC:ADC &7C:AND #&7:TAY:LDA Y%,Y:LDY #0:STA (&7A),Y:INY:STA (&7A),Y:INY:STA (&7A),Y:INY:STA (&7A),Y
INY:STA (&7A),Y:INY:STA (&7A),Y:INY:STA (&7A),Y:INY:STA (&7A),Y:LDA #&F0:BIT &74:BNE e:LDA #&2:BIT &72:BNE k:JMP f:.e LDA #&2:BIT &72:BNE f:JMP k:.f LDA &73:CLC:ADC #1:AND #7:STA &73:JMP i:.k LDA &73:CLC:ADC #7:AND #7:STA &73:.i CLC:LDA &78:ADC #&80:STA &78
LDA &79:ADC #2:STA &79:LDA &74:CLC:ADC #1:STA &74:CMP #32:BNE l:LDA &76:CLC:ADC #64:STA &76:LDA &77:ADC #0:STA &77:LDA &72:CLC:ADC #1:STA &72:CMP #10:BEQ r:JMP a:.r LDA &7C:CLC:ADC #&1:AND #&7:STA &7C:JMP c:RTS:]:NEXT:MODE 0:VDU23,1,0;0;0;0;:*FX19
CALL g

(raw output)

Plot and VDU reference

The ASCII table (also for VDU codes) and the PLOT codes.

Either float text in editor or table on the right

"Change All Occurrences" doesn't work well

Cut and paste this into owlet:

F.F=F TOF S.F:READF$:F%=F*LENF$:P.F$,F%:N.
D.F

Then right click on one of the F variables in the code and select "Change All Occurrences", then type X. The program now looks like this:

X.X=X TOF S.X:READF$:X%=X*LENF$:P.X$,X%:N.
D.X

I'd expect it only to change uses of the variable F, but it's also changed:

  • F. is FOR abbreviated
  • F$ and F% are also matched when not preceded by a keyword
  • F in D.F is really a string constant not the variable F in this program (though if it were read into a numeric variable it would be a the variable F so this one more forgivable)

It's also failed to match variable F when preceded by a keyword (TOF). I guess it assumes C-like tokenisation rules.

I can see this feature would be handy for golfing code if it actually worked, but if it can't be persuaded to understand BBC BASIC tokenisation rules then perhaps it would be better turned off in owlet. When I first tried it on a real example it looked like it had worked, but actually it had missed a use of the variable, and so broke the code.

Implement "Rheolism" method to pass tokenized code through Twitter

I haven't checked if the 'official' BBC BASIC byte tokens we generate fail when parsed by Twitter, but Rheolism did a fair amount of testing and discovered certain byte tokens need ANDing (doh) ORing with a high byte to make in through unscathed.

As shown in https://github.com/8bitkick/BBCMicroBot/blob/7bf7435d70cde7892d69c12bf5b934b0ee068ee2/tools/bbcbasictokenise#L17 by @ojwb

This may also fix issues with some bytes not being rendered as characters in the editor as he also reported

Handle TIMER and other continuation things

TIMER=1
P.TIMER

is tokenised as TIMER and not TIME R.

http://www.benryves.com/bin/bbcbasic/manual/Appendix_Tokeniser.htm

Though...I just tried this and filtering on the "continuation" bit doesn't account for the fact that TIME appears twice in the tokenisation table. Once as TIME (PMC bits set) and TIME (no special bits set). I'm not sure how BASIC handles this case. I am confuse.

    it("should not tokenise continuation tokens followed by alphanum", () => {
        checkTokens(["TIMER"], [{offset: 0, type: "variable"}]);
    });

should pass

@%

I'd expect @% to be highlighted just like A% (since they're both resident integer variables) but in A%=@%:@%=A% @% is green (looks like a slightly paler green than numbers).

It's true that the value of @% is used for formatting numbers, but other resident integer variables have special properties too (A%, C%, X%, Y% in CALL and USR; O% and P% in assembler).

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.