![]() |
Forum Index : Microcontroller and PC projects : big ben clock problems
Author | Message | ||||
oldtimer Newbie ![]() Joined: 02/12/2016 Location: AustraliaPosts: 18 |
Hi to all I have recently been trying to get Matherp,s Big Ben clock running on an explore 100 with the 5 inch lcd backpack - I have cut and pasted the associated code -which was attached to the post -"the impossible takes a little longer"- into MM EDIT- and also resized the bitmap image to 480 by 480 pixels on the SD card- when I run the program I first get a nice ,screen filling picture of the bitmap followed - a few seconds later - by a small red circle at the centre of the image - this also remains for a few seconds at which point the display degenerates into random horizontal and vertical lines and colours - the error message "read buffer is 93.12 -or 116.5- or some other random number - used" followed by "pin 30 is invalid" is anyone able to suggest a possible fix to allow the beautiful Big Ben clock shown in the post -to display - complete with moving hands Im new to this forum so not sure if my thanks to Panky and lew 247 for their help was directed to them many thanks |
||||
oldtimer Newbie ![]() Joined: 02/12/2016 Location: AustraliaPosts: 18 |
figured out the pin 30 problem- I didnd realise that the program was for the 64 pin chip - ive now changed the RD pin to 27 but still get the same error message "read buffer is 90 something % used" and the screen dissolving into a mass of horizontal and vertical lines after the bitmap display would appreciate any helpful advice |
||||
matherp Guru ![]() Joined: 11/12/2012 Location: United KingdomPosts: 10379 |
Are you using the 100-pin version of the CFunction which is on page 2 of the post? This effect can actually now be done without a CFunction using the new BLIT and TRIANGLE commands in 5.3 Have a look at this code which does the Photo-realistic gauge demo without needing to use a CFunction option explicit option default none ' const Y_top = 0 'Y coordinate of top of the image file on the screen const X_left = 160 'X coordinate of left of the image file on the screen const Y_point = 320 'Y coordinate of the centre of the pointer relative to the image top const X_point = 240 'X coordinate of the centre of the pointer relative to the image left ' const buffersize = 1000 'used to store the image data behind the pointer dim integer buff(buffersize) ' ' ' Now we define the pointer as the X,Y coordinates of a number of triangles with the rotation point at 0,0 ' It is simplest to define this in the 12-oclock position which means the Y-coordinates at the top of the pointer will be negative ' The order of data elements in the array is: ' t1x1,t1y1,t1x2,t1y2,t1x3,t1y3, t2x1,t2y1,t2x2,t2y2,t2x3,t2y3,...tntx1,tnty1,tntx2,tnty2,tntx3,tnty3 ' dim integer nt=4 'Number of triangles used to define the pointer dim integer ptr(5,nt-1)=(-4,-35, -4,-130, 4,-35, -4,-130, 4,-130, 4,-35, -4,-35,-8,-35,-4,-130, 4,-35,8,-35,4,-130) DIM INTEGER pcolour=rgb(171,52,32) 'define the colour of the pointer const pivot=35 'diameter in pixels of the fulcrum of the pointer ' dim integer xx0(nt-1),yy0(nt-1),xx1(nt-1),yy1(nt-1),xx2(nt-1),yy2(nt-1),tcol(nt-1) dim integer i dim integer x,y,w,h ' cls load image "rtecop8.bmp",X_left,Y_top ' ' demo code moving the pointer dim float demoangle=-45 for i=0 to nt-1 'load the coordinate arrays rotatetriangle(i,pcolour,demoangle,X_point+X_left,Y_point+Y_top,ptr(0,i),ptr(1,i),ptr(2,i),ptr(3,i),ptr(4,i),ptr(5,i)) 'rotate the pointer into the drawing array next i getlimits(x, y, w, h) blit read #1, x, y, w, h for i=0 to nt-1 triangle xx0(i), yy0(i), xx1(i), yy1(i), xx2(i), yy2(i), tcol(i),tcol(i) next i do do drawpointer(demoangle) demoangle=demoangle+1 loop while demoangle <=45 do drawpointer(demoangle) demoangle=demoangle-1 loop while demoangle >=-45 loop ' Sub drawpointer(angle as float) local integer last_x=x, last_y=y, last_w=w, last_h=h, i for i=0 to nt-1 rotatetriangle(i,pcolour,angle,X_point+X_left,Y_point+Y_top,ptr(0,i),ptr(1,i),ptr(2,i),ptr(3,i),ptr(4,i),ptr(5,i)) 'rotate the pointer into the drawing array next i getlimits(x, y, w, h) do i=getscanline() loop while (i>409 or i<400) blit WRITE #1, last_x, last_y, last_w, last_h blit close #1 blit read #1, x, y, w, h for i=0 to nt-1 triangle xx0(i), yy0(i), xx1(i), yy1(i), xx2(i), yy2(i), tcol(i),tcol(i) next i drawpivot End Sub ' ' Routine to find the coordinates of the area to be saved by BLIT READ ' sub getlimits(x as integer, y as integer, w as integer, h as integer) Local integer i,max_x=0,min_x=MM.HRES,max_y=0,min_y=MM.VRES for i=0 to nt-1 if(xx0(i)>max_x)then max_x=xx0(i) if(xx1(i)>max_x)then max_x=xx1(i) if(xx2(i)>max_x)then max_x=xx2(i) if(xx0(i)<min_x)then min_x=xx0(i) if(xx1(i)<min_x)then min_x=xx1(i) if(xx2(i)<min_x)then min_x=xx2(i) if(yy0(i)>max_y)then max_y=yy0(i) if(yy1(i)>max_y)then max_y=yy1(i) if(yy2(i)>max_y)then max_y=yy2(i) if(yy0(i)<min_y)then min_y=yy0(i) if(yy1(i)<min_y)then min_y=yy1(i) if(yy2(i)<min_y)then min_y=yy2(i) next i x=min_x y=min_y w=max_x-min_x+1 h=max_y-min_y+1 end sub sub rotatetriangle(n as integer, col as integer, angle as float, x as integer, y as integer, x0 as integer, y0 as integer, x1 as integer, y1 as integer, x2 as integer, y2 as integer) local float sine=sin(rad(angle)),cosine=cos(rad(angle)) local integer x0a,y0a,x1a,y1a,x2a,y2a x0a= x0*cosine - y0 * sine + x y0a= y0*cosine + x0 * sine + y x1a= x1*cosine - y1 * sine + x y1a= y1*cosine + x1 * sine + y x2a= x2*cosine - y2 * sine + x y2a= y2*cosine + x2 * sine + y xx0(n)=x0a yy0(n)=y0a xx1(n)=x1a yy1(n)=y1a xx2(n)=x2a yy2(n)=y2a tcol(n)=col end sub ' sub drawpivot() 'put anything you like here to draw the fulcrum as you wish circle X_point+X_left,Y_point+Y_top,pivot,0,,,rgb(54,54,54) circle X_point+X_left,Y_point+Y_top,pivot*0.9,0,,,rgb(43,43,43) end sub |
||||
lew247![]() Guru ![]() Joined: 23/12/2015 Location: United KingdomPosts: 1702 |
Matherp Is it possible to have two dials with the same centre point working independantly? for example a thermometer dial showing both indoor and outdoor temp's at the same time but updating independantly? and with each having a different colour hand? |
||||
matherp Guru ![]() Joined: 11/12/2012 Location: United KingdomPosts: 10379 |
Sounds like the hands of a clock ![]() |
||||
lew247![]() Guru ![]() Joined: 23/12/2015 Location: United KingdomPosts: 1702 |
oh my god, how stupid am I... Sorry I should have realised |
||||
TrevorH Senior Member ![]() Joined: 06/04/2018 Location: United KingdomPosts: 145 |
I am trying to get the above code to work on a Picomite with ssd1963 TFT. I know this is an old topic but I wanted to create some large gauges that the pointer didn't wipe the background. I get a "dimension" error at the line 'i=getscanline()'. Was 'getscanline' only available on the 100+ where it works flawlessly, or is there an alternative? |
||||
phil99![]() Guru ![]() Joined: 11/02/2018 Location: AustraliaPosts: 2679 |
PicoMiteVGA manual GETSCANLINE This will report on the line that is currently being drawn on the VGA monitor in the range of 0 to 525. This is irrespective of the current MODE. Using this to time updates to the screen can avoid timing effects caused by updates while the screen is being updated. The first visible line will return a value of 0. Any line number above 479 is in the frame blanking period. But it isn't in the PicoMite LCD manual, so I guess it isn't implemented on LCDs. |
||||
Bleep Guru ![]() Joined: 09/01/2022 Location: United KingdomPosts: 659 |
getscanline isn't relivent to a LCD display, so won't be in that version of MMBasic, LCDs are not scanned, at least not in the sense of a monitor or TV screen, there is no update rate or frame rate, you simply send the appropriate graphics commands to the display and it displays what you or MMBasic have asked for. Regards Kevin. |
||||
matherp Guru ![]() Joined: 11/12/2012 Location: United KingdomPosts: 10379 |
Actually, they are scanned exactly like a television. Most LCD controllers have commands to allow you to read the scanline. However, this can only be done if you can read from the display in the first place. So in PicoMite terms this would be on displays that support BLIT. ILI9341, ILI9488 (possibly), and SSD1963 could be possible but this hasn't been implemented. ![]() Edited 2022-10-10 18:39 by matherp |
||||
TrevorH Senior Member ![]() Joined: 06/04/2018 Location: United KingdomPosts: 145 |
@matherp is there a way to read in the background portion without getscanline, I think when cfunctions were used the triangles functions had a read background ability. For large gauges or clocks saving ALL the background is not possible (memory limitations). |
||||
TrevorH Senior Member ![]() Joined: 06/04/2018 Location: United KingdomPosts: 145 |
My understanding of how displays work as in tv or vga regarding scanline is VERY limited, I have got the program working in a fashion by commenting out "i=getscanline" and setting "i=400". But the pointer is flickering, so I guess the scanline is fixing the time to write out the pointer and the blit background to make it smoother (it is a guess). is there another way to fix the flickering?? |
||||
lew247![]() Guru ![]() Joined: 23/12/2015 Location: United KingdomPosts: 1702 |
Try this I think it's when I had a clock with a weather readout on the bottom but I can't remember for sure It was definitely using an SSD1963 display though If it has the weather you can cut those bits out of the code and reposition/resize the hands '***Thanks to Matherp for his help with the hands*** cls RGB(white) option explicit option default none dim integer buff(480*480*3/8-1) dim integer nt=4 'Number of triangles being updated dim integer xx0(nt-1),yy0(nt-1),xx1(nt-1),yy1(nt-1),xx2(nt-1),yy2(nt-1),tcol(nt-1),secs,mins,hours,first=1 dim integer oldsecs,i DIM STRING q$=chr$(34) dim x$,z$,Temp$,Wind$,prob$,type$,summary$ dim integer val1 Dim INTEGER a(90000) DIM allObs$(16) SetTick 30000,weather,1 'every 15 minutes load image "4.bmp",0,0 circle 240,240,238,3,1,RGB(black) blit read #1,0,0,480,480 option autorefresh off FONT 4,2 i = 0 secs=val(right$(time$,2)) mins=val(mid$(time$,4,2)) hours=val(left$(time$,2)) mod 12 Text 100,530, day$(now) , LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Day Text 70,590, date$ , LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Date weather do secs=val(right$(time$,2)) mins=val(mid$(time$,4,2)) hours=val(left$(time$,2)) mod 12 if secs <> oldsecs then hands(secs,mins,hours,(MM.HRES\2-MM.HRES\12),MM.Hres\2, MM.HRES\2) end if mins = 0 and secs = 0 elseif mins = 15 and secs = 0 elseif mins = 30 and secs = 0 elseif mins = 45 and secs = 0 then weather pause 500 end if if time$ = "00:00:00" then Text 100,530, " ") , LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Clear Day Text 100,530, day$(now) , LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Day Text 70,590, " ", LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Clear Date Text 70,590, date$ , LB, 4, 2, RGB(BLACK),RGB(WHITE) 'Date pause 950 end if BOX 2, 620, 476, 175, 3, RGB(black) ' text i,650,x$ ' text i+mm.fontwidth*len(z$),720,z$ ' refresh ' i = i - 2 ' if i < -mm.fontwidth*len(z$) then : i = 0 : endif ' text i,720,z$ ' text i+mm.fontwidth*len(x$),720,x$ ' refresh ' i = i - 2 ' if i < -mm.fontwidth*len(x$) then : i = 0 : endif ' oldsecs = secs loop end sub weather system "wget -q -O- "+q$+"https://swd.weatherflow.com/swd/rest/observations/station/10170?api_key=20c70eae-e62f-4d3b-b3a4-8586e90f3ac8"+q$,a() pause 700 on error IGNORE JSON$(a(),"obs[0].air_temperature")'time received Temp$ = JSON$(a(),"obs[0].air_temperature")+"`C " Wind$ = JSON$(a(),"obs[0].wind_avg")+"MPH " 'prob$ = JSON$(a(),"obs[0].air_temperature") 'rain 'type$ = JSON$(a(),"obs[0].air_temperature") 'rain summary$ = JSON$(a(),"obs[0].uv") Text 60,660, " ",LB, 4, 1, RGB(BLACK),RGB(WHITE) Text 60,660, "Temperature "+ Temp$ , LB, 4, 1, RGB(BLACK),RGB(WHITE) Text 60,700, " ",LB, 4, 1, RGB(BLACK),RGB(WHITE) Text 60,700, "Windspeed "+ Wind$, LB, 4, 1, RGB(BLACK),RGB(WHITE) Text 60,740, " ",LB, 4, 1, RGB(BLACK),RGB(WHITE) Text 60,740, "UV Index "+ summary$ , LB, 4, 1, RGB(BLACK),RGB(WHITE) 'val1 = val(prob$) 'val1 = val1 * 100 'print val1, "Val1" 'if val1 >= 1 then ' print val1 ' Text 60,780, " ",LB, 4, 1, RGB(BLACK),RGB(WHITE) ' Text 60,780, STR$(val1)+ "% chance of "+type$, LB, 4, 1, RGB(BLACK),RGB(WHITE) ' elseif val1 < 1 then ' Text 60,780, " ",LB, 4, 1, RGB(BLACK),RGB(WHITE) 'end if 'print STR$(val1), "Val" print Wind$ end sub Sub hands(seconds As integer, minutes as integer, hours as integer, size as integer, x as integer, y as integer) Local integer x1,y1,x2,y2,x0,y0,i local float angle=seconds*6 rotatetriangle(2,RGB(RED),angle,x,y,-3,50,3,50,-3,-size) 'make up the second hand with two triangles rotatetriangle(3,RGB(RED),angle,x,y,3,-size,3,50,-3,-size) angle=minutes*6 + seconds/10 rotatetriangle(0,RGB(black),angle,x,y,-size/20,0,size/20,0,0,-size*1.04) ' Minute hand angle=hours*30 + minutes/2 rotatetriangle(1,RGB(black),angle,x,y,-size/20,0,size/20,0,0,-size*0.78) ' Hour hand blit write #1,0,0 triangle xx0(), yy0(), xx1(), yy1(), xx2(), yy2()) ,tcol() ,tcol() Circle x,y, size\16, 0, , rgb(red), rgb(red)) Circle x,y, size\20, 0, , 0, 0 Circle x,y, size\24, 0, , RGB(red), RGB(red) refresh End Sub sub rotatetriangle(n as integer, col as integer, angle as float, x as integer, y as integer, x0 as integer, y0 as integer, x1 as integer, y1 as integer, x2 as integer, y2 as integer) local float sine=sin(rad(angle)),cosine=cos(rad(angle)) local integer x0a,y0a,x1a,y1a,x2a,y2a x0a= x0*cosine - y0 * sine + x y0a= y0*cosine + x0 * sine + y x1a= x1*cosine - y1 * sine + x y1a= y1*cosine + x1 * sine + y x2a= x2*cosine - y2 * sine + x y2a= y2*cosine + x2 * sine + y xx0(n)=x0a yy0(n)=y0a xx1(n)=x1a yy1(n)=y1a xx2(n)=x2a yy2(n)=y2a tcol(n)=col end sub [/q] |
||||
lew247![]() Guru ![]() Joined: 23/12/2015 Location: United KingdomPosts: 1702 |
This is Peter's post for an E100 with the clock working from this thread Edited 2022-10-12 02:18 by lew247 |
||||
TrevorH Senior Member ![]() Joined: 06/04/2018 Location: United KingdomPosts: 145 |
Hi lew, thanks for replying to my queries. Your first post ie the weather program won't work as the Pico has not enough memory available in one slot for the very large buffer (unless you know how to use 2nd slot for a buffer). The E100 has bigger memory available for one program. Your second post is using cfunctions which are not available on the Pico (yet). The program I was playing with was put together by Peter to use the new triangles function and NO cfunctions, it cleverly reads the background to be replaced when the pointer has moved, but does use getscanline (not implemented on Pico) to avoid flickering. I don't understand how getscanline achieves this non-flickering. |
||||
JohnS Guru ![]() Joined: 18/11/2011 Location: United KingdomPosts: 4068 |
Er... I think they are. John |
||||
TrevorH Senior Member ![]() Joined: 06/04/2018 Location: United KingdomPosts: 145 |
Hi John, thanks for your input, I'm a bit late to the Pico party and as such had not seen the thread on Csubs. |
||||
![]() |
![]() |
The Back Shed's forum code is written, and hosted, in Australia. | © JAQ Software 2025 |