Alarm clock radio with 303WIFILC01 and RDA5807M

Place your projects here
Post Reply
User avatar
Fernando Perez
Posts: 378
Joined: Mon Feb 15, 2021 10:09 pm
Location: Santander (Spain)
Has thanked: 195 times
Been thanked: 267 times

Alarm clock radio with 303WIFILC01 and RDA5807M

Post by Fernando Perez »

At [Local Link Removed for Guests] I wrote about the RDA5807M FM radio module and at [Local Link Removed for Guests] on the clock module 303WIFILC01.
I could not resist joining the two modules to obtain a small alarm clock radio:

https://youtu.be/LLS2-pT456g

This is the program:

Code: [Local Link Removed for Guests]

' Clock Radio with 303WIFILC01 and RDA5807
' Files: radioClock.bas / main.css / reloj.png

' replace with the weekday names in your country:
dim weekDay$(6) = "Lunes","Martes","Miercoles","Jueves","Viernes","Sábado","Domingo"
dim alarmDate$(6)

' variables and default values:
' if any file is missing, go create it
' -----------------------------------------------------
volume=0 : brightness=0 : chosen=0 : duration = 0
file$ = "/defaults.dat"
if file.exists(file$) then LOAD_VAR volume, brightness, chosen, duration, file$ else SAVE_VAR volume, brightness, chosen, duration, file$
' -----------------------------------------------------
index = 6
dim isCheck(index) = 1, 1, 1, 1, 1, 0, 0
dim alarmTime$(index) = "08:00","08:00","08:00","08:00","08:00","10:00","10:00"
file$ = "/weekly.dat"
if file.exists(file$) then LOAD_ARRAYS index, isCheck(), alarmTime$(), file$ else SAVE_ARRAYS index, isCheck(), alarmTime$(), file$
' -----------------------------------------------------
index = 3
' replace with the frequency and abbreviation of your favorite stations:
dim freq(index) = 93.0, 96.9, 102.9, 105.0
dim station$(index) = "RNE Clasica","RNE 1","RNE 3","RNE 5"
file$ = "/stations.dat"
if file.exists(file$) then LOAD_ARRAYS index, freq(), station$(), file$ else SAVE_ARRAYS index, freq(), station$(), file$
' -----------------------------------------------------
numDay = 0
nextDateAlarm$ = ""
nextTimeAlarm$ = ""

' =================================
' 303WIFILC01 config and turning on 
' Dot display control
noDot=0 : dot1=2 : dot3=8 : colon=4 : led=0
' numbers from zero to nine, blank space and minus sign:
dim font(11) = 252, 132, 186, 174, 198, 110, 126, 164, 254, 238, 0, 2

i2c.setup 13, 12    ' SDA and SCL on the 303WIFILC01
TM_init brightness

radio_On = 0
playing = 0
RDA_Init volume, 0  ' 0 = radio Off

timer0 1000, displayClock

onHtmlReload web
onHtmlChange update
stage = 1 : today = 0 : wakeUp$ = ""
gosub getNext
gosub web

pin.mode 0, input, pullup  ' radio on/off button
interrupt 0, radioSwitch

WAIT ' wait for something to happen
END

' -----------
displayClock:
  ' tomorrow
  hour$ = left$(time$,2) + mid$(time$, 4, 2)
  if led=0 then led=4 else led=0
  TM_show hour$, led
  ' Check if it is alarm time
  second$= right$(time$, 2)
  if second$ = "00" then     ' new minute
    weekDay date$, today     ' what weekday is today
    if isCheck(today) then   ' if it is marked for alarm
      wakeUp$ = replace$(alarmTime$(today), ":", "") ' remove colon from alarm time
'      wlog wakeUp$, hour$
      if wakeUp$ = hour$ then RDA_Init volume, 1  
    endif
  endif
  ' check if turn off radio
  if millis-radio_On >= duration * 60 * 1000 then RDA_Init volume, 0
return

' ----------------
web:
  cls
  cssexternal "/main.css"
  a$ = ""
  select case stage
    case 1
      a$ = a$ + |<div class="main">|
      a$ = a$ + |<img src="reloj.png">|
      a$ = a$ + |<h1>Current value</h1>|
      a$ = a$ + |<table>|
      a$ = a$ + |<tr><td><p style="margin-right:25px;">Clock brightnes</p></td><td class="enhanced"><h3>|+str$(brightness)+|</h3></td></tr>|
      a$ = a$ + |<tr><td><p>Radio volume</p></td><td class="enhanced"><h3>|+str$(volume)+|</h3></td></tr>|
      a$ = a$ + |<tr><td><p>Selected station</p></td><td class="enhanced"><h3>|+station$(chosen)+|</h3></td></tr>|
      a$ = a$ + |<tr><td><p>Radio ON time</p></td><td class="enhanced"><h3>|+str$(duration)+|</h3></td></tr>|
      a$ = a$ + |<tr><td><p>Next day alarm</p></td><td class="enhanced"><h3>|+nextDateAlarm$+|</h3></td></tr>|
      a$ = a$ + |<tr><td><p>Next hour alarm</p></td><td class="enhanced"><h3>|+nextTimeAlarm$+|</h3></td></tr>|
      a$ = a$ + |</table>|
      a$ = a$ + button$("Radio Setup", radioSetup, "button")  
      a$ = a$ + button$("Alarm Setup", alarmSetup, "button") 
      a$ = a$ + |</div>|

    case 2
      a$ = a$ + |<div class="hora">|
      a$ = a$ + |<table>|
      a$ = a$ + |<th colspan=2"><h1>Daily Alarm</h1></th>|
      for i = 0 to 6
        a$ = a$ + |<tr><td><input type="checkbox" data-var="isCheck(| + str$(i) + |)" onchange="cmdChange(event)"></td>|  
        a$ = a$ + |<td><input type="Time" data-var="alarmTime$(| + str$(i) + |)" onchange="cmdChange(event)" value="| + alarmTime$(i) + |"></td>|
        a$ = a$ + |<td><p>| + weekDay$(i) + |</p></td></tr>|  
      next i
      a$ = a$ + |</table>|
      a$ = a$ + button$("Radio Setup", radioSetup, "button")  
      a$ = a$ + button$("Done", done, "button") 
      a$ = a$ + |</div>|  

    case 3
      a$ = a$ + |<div class="emisora">|
      a$ = a$ + |<h1>Waking up with:</h1>|
      a$ = a$ + |<table>|
      ' ====================== TEXTBOX & RADIOBUTTON ============================================
      a$ = a$ + |<th><p>MHz</p></th><th><p>Station</p></th><th><p>Sel</p></th>|
      for i = 0 to index
        a$ = a$ + |<tr>|
        a$ = a$ + |<td><input type="textbox" onchange="cmdChange(event)" data-var="freq(| + str$(i) + |)" class="mhz"></td>|
        a$ = a$ + |<td><input type="textbox" onchange="cmdChange(event)" data-var="station$(| + str$(i) + |)" class="station"></td>| 
        a$ = a$ + |<td><input type="radio"   onchange="cmdChange(event)" data-var="chosen" name="station" value="| + str$(i) + |"|
        if i = chosen then a$ = a$ + |checked|
        a$ = a$ + |></td></tr>|
      next i
      a$ = a$ + |</table><br>|
      ' ========================================  SLIDERS ======================================= 
      a$ = a$ + |<h2>Volume</h2>|
      a$ = a$ + |<div class="slider"><input type="range" onchange="cmdChange(event)" data-var="volume" |
      a$ = a$ + |min="0" max="15" oninput="rg1.innerText=this.value"><p id="rg1">|+str$(volume)+|</p></div>|
      a$ = a$ + |<h2>Brightness</h2>|
      a$ = a$ + |<div class="slider"><input type="range" onchange="cmdChange(event)" data-var="brightness" |
      a$ = a$ + |min="1" max="8" oninput="rg2.innerText=this.value"><p id="rg2">|+str$(brightness)+|</p></div>|
      a$ = a$ + |<h2>Duration</h2>|
      a$ = a$ + |<div class="slider"><input type="range" onchange="cmdChange(event)" data-var="duration" |
      a$ = a$ + |min="0" max="60" oninput="rg3.innerText=this.value"><p id="rg3">|+str$(duration)+|</p></div>|

      ' ======================================== BUTTONS ========================================  
      a$ = a$ + button$("Alarm Setup", alarmSetup, "button")
      a$ = a$ + button$("Done", done, "button")  
      a$ = a$ + |</div>|
    end select
    
    html a$
    refresh
    a$ = ""
    wlog ramfree
return

' ----------------
alarmSetup:
  stage = 2
  gosub web
return

' ----------------
done:
  stage = 1
  gosub web
return

' ----------------
radioSetup:
  stage = 3
  gosub web
return

' ----------------
radioSwitch:
  if pin(0) = 0 then return
' Radio On/Off
  playing = 1 - playing
  if playing = 0 then RDA_Init volume, 0 else RDA_Init volume, 1
return

' ----------------
update:
  wlog "update of "; HtmlEventVar$; " since stage "; stage

  select case stage
    case 2 ' Alarm Setup
      gosub getNext
      SAVE_ARRAYS 6, isCheck(), alarmTime$(), "/weekly.dat"
    case 3 ' Radio Setup
      SAVE_VAR volume, brightness, chosen, duration, "/defaults.dat"
      SAVE_ARRAYS 3, freq(), station$(), "/stations.dat"
      if HtmlEventVar$ = "brightness" then TM_init brightness
      if HtmlEventVar$ = "volume" then RDA_Init volume, 1
      
  end select     

  refresh
return

' ---------------
getNext:
  for i = 1 to 7
    nextDay$ = unixDate$(dateUnix(date$) + (86400*i))
    weekDay nextDay$, numDay
    alarmDate$(numDay) = nextDay$
  next i  
  
  weekDay date$, numDay
  if isCheck(numDay) then
    if left$(time$, 5) < alarmTime$(numDay) then
      nextDateAlarm$ = date$
      nextTimeAlarm$ = alarmTime$(numDay)
      return
    endif  
  endif
  
  for i = 1 to 6
    numDay = numDay + 1
    if numDay = 7 then numDay = 0
    if isCheck(numDay) then
      nextDateAlarm$ = alarmDate$(numDay)
      nextTimeAlarm$ = alarmTime$(numDay)
      return  
    endif
  next i
 
  nextDateAlarm$ = "NONE"
  nextTimeAlarm$ = "NONE"
 
return

'------------------------
SUB weekDay(day$, numDay)
dim remap(6) = 5, 6, 0, 1, 2, 3, 4
  numDay = ((((dateunix(day$)-dateunix("01/01/00")))/(24*3600)) mod 7)
  numDay = remap(numDay)
END SUB



' ********** Save/retrieve variables in SPIFFS **********
SUB LOAD_VAR(var1, var2, var3, var4, fileName$)
LOCAL line$
  line$ = file.read$(fileName$)
  var1 = val(word$(line$, 1, ","))
  var2 = val(word$(line$, 2, ","))
  var3 = val(word$(line$, 3, ","))
  var4 = val(word$(line$, 4, ","))    
END SUB

' ---------------------------------------------------
SUB LOAD_ARRAYS(index, arrayN(), arrayC$(), fileName$)
LOCAL i, line$
  for i = 0 to index
    line$ = file.read$(filename$, i+1)
    arrayN(i) = val(word$(line$, 1, ","))
    arrayC$(i) = replace$(word$(line$, 2, ","), chr$(13), "") ' remove cr from end of line 
  next i
END SUB

' -------------------------------------
SUB SAVE_VAR(var1, var2, var3, var4, fileName$)
LOCAL line$
  line$ = str$(var1) + "," + str$(var2) + "," + str$(var3) + "," + str$(var4)
  file.save fileName$, line$
END SUB

' ---------------------------------------------------
SUB SAVE_ARRAYS(index, arrayN(), arrayC$(), fileName$)
LOCAL r, i, line$
  r = file.delete(fileName$)
  for i = 0 to index
    line$ = str$(arrayN(i)) + "," + arrayC$(i) + chr$(13) + chr$(10) ' append cr+lf to end of line
    file.append fileName$, line$
  next i
END SUB

' ********** 303WIFILC01 clock board **********
SUB TM_init(brightness)
LOCAL value
  value = (16 * brightness) + 1  
  if brightness = 8 then value = 1 ' brightness 1 (min) to 8 (max)
  i2cWrite &H24, value
END SUB
  
' ----------------------
SUB TM_show(line$, dots)
LOCAL i, value, remap
  for i = 1 to 4
    value = asc(mid$(line$, i, 1)) - 48  ' 0 = ascii 48
    if value = -16 then value = 10       ' blank space
    if value = -3 then value = 11        ' minus sign
    remap = font(value)
    select case dots
      case colon : if i = 2 then remap = remap +1
      case dot1  : if i = 1 then remap = remap + 1
      case dot3  : if i = 3 then remap = remap +1
    end select
    i2cWrite &H33 + i, remap
  next i  
END SUB

' --------------------------
SUB i2cWrite(address, value)
  i2c.begin address
  i2c.write value
  i2c.end
END SUB

' ********** RDA5807 FM Radio tuner **********
SUB RDA_Init(volume, enable)
LOCAL level
  if enable then radio_On = millis ' init measure time ON
  pin.mode 1, output ' set pin TX as output
  pin.mode 3, output ' set pin RX as output
  i2c.setup 1, 3     ' SDA and SCL on RAD5807
  address = &H11     ' I2C device address
  level = volume OR &H80
  ioBuff.dim(0,4) = &HD0, enable, &H08, level

  ' init RDA5807
  i2c.write_ioBuff(0, 0, 2), address, &H02
  i2c.write_ioBuff(0, 2, 2), address, &H05

  ' tunein sation
  tuneIn freq(chosen)

  ' restore settings
  pin.mode 1, SPECIAL
  pin.mode 3, SPECIAL
  i2c.setup 13, 12    ' SDA and SCL on the 303WIFILC01
END SUB

' --------------------------------------------
SUB tuneIn(frequency)
LOCAL channel, hightByte, lowByte
  channel = ((frequency * 100) - 8700) / 10
  hightByte = channel >> 2
  lowByte = (channel << 6) OR &H10
  lowByte = lowByte AND &HFF
  
  ioBuff.dim(1, 2) = hightByte, lowByte
  i2c.write_ioBuff(1), address, &H03
END SUB

' ***********  FIN *****************
This is the CSS file:

Code: [Local Link Removed for Guests]

body {
  margin: 0 auto;
  text-align: center;
}

p {
  font-family: "trebuchet ms";
  font-size: 1.2rem;
  margin: 5px 0px 5px 0px;
  padding-left: 10px;
  text-align: left;
}

h1 {
  font-family: "trebuchet ms";
  font-size: 2rem;
  margin: 10px;
}

h2 {
  font-family: "trebuchet ms";
  font-size: 1rem;
  margin: 0px 0px 30px 0px;
}

h3 {
  font-family: "trebuchet ms";
  font-size: 1.2rem;
  margin: 0;
  text-align:center;
}

table {
  margin:0 auto;
  padding: 0px;
}

th p {
  text-align:center;
}

.enhanced {
  border:solid 1px blue;
  background-color:#F0E68C;
  width:150px;
}

#button {
  display: inline-block;
  margin: 20px 10px 20px 25px;
  padding: 10px 20px;
  border: none;
  border-radius: 16px;
  color: black;
  background-color: #ddd;
  text-align: center;
  font-size: 1.2rem;
  font-weight: 600; 
  cursor: pointer;
  box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2), 0 6px 20px 0 rgba(0,0,0,0.19);
}

.hora input {
  font-family: verdana;
  font-size: 1.5rem;
  font-weight: 600;
  text-align: center;
  margin: 0px;
  padding: 0px;
  height: 40px;
  width: 10rem;
}
.hora input[type="checkbox"] {
  width: 40px;
 }

.emisora .mhz {
  background-color:#FAEBD7;
  font-size:15px;
  width:80px;
}
.emisora .station {
  background-color:#F0FBD7;
  font-size:15px;
  width:150px;
}
.emisora input {
  font-family: verdana;
  font-size: 15px;
  font-weight: 600;
  text-align: center;
  margin: 3px;
  padding: 8px;
  height: 40px;
  width: 15rem;
}
.emisora input[type="radio"] {
  margin-left: 15px;
  width: 30px;
  height: 30px;
 }

.slider {
 position:relative;
 top:70%;
 left:50%;
 transform:translate(-50%,-50%);
 width:220px;
 height:25px;
 padding:10px;
 padding-left: 40px;
 background:#FFF8DC;
 border-radius:20px;
 display:flex;
 align-items:center;
 box-shadow:0px 15px 40px #7E6D5766;
}
.slider p {
 font-size:26px;
 font-weight:600;
 font-family: Open Sans;
 margin: 30px 0px;
 padding-left:30px;
 color:#7E6D57;
}
.slider input[type="range"] {
 -webkit-appearance:none !important;
 width:420px;
 height:2px;
 background:#7E6D57;
 border:none;
 outline:none;
}
.slider input[type="range"]::-webkit-slider-thumb {
 -webkit-appearance:none !important;
 width:30px;
 height:30px;
 background:#fcfcfc;
 border:2px solid #7E6D57;
 border-radius:50%;
 cursor:pointer;
}
.slider input[type="range"]::-webkit-slider-thumb:hover {
 background:#7E6D57;
}
You do not have the required permissions to view the files attached to this post.
Last edited by Fernando Perez on Sun Apr 09, 2023 9:51 pm, edited 2 times in total.
User avatar
Fernando Perez
Posts: 378
Joined: Mon Feb 15, 2021 10:09 pm
Location: Santander (Spain)
Has thanked: 195 times
Been thanked: 267 times

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by Fernando Perez »

Leafing through this year's March/April issue of Elektor, I come across an article about a similar project.
For legal reasons I cannot publish the link to the extract that I have uploaded to Mega, but I will gladly provide it to whoever requests it by private message.
My request is: If any of you have access, by being an Elektor subscriber, to download the software associated with that assembly, can you provide it to me? Thank you.

https://www.elektormagazine.com/labs/cloc-le-reveil-20#
User avatar
PeterN
Posts: 366
Joined: Mon Feb 08, 2021 7:56 pm
Location: Krefeld, Germany
Has thanked: 171 times
Been thanked: 203 times
Contact:

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by PeterN »

Hi Fernando
I hope my email solved the problem?
User avatar
Fernando Perez
Posts: 378
Joined: Mon Feb 15, 2021 10:09 pm
Location: Santander (Spain)
Has thanked: 195 times
Been thanked: 267 times

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by Fernando Perez »

Hello Peter.
I have just sent you a private message informing you that I have not received any message from you.
Curiously, my message does not appear in the "sent messages" folder nor is it even in the "Outbox" folder. Could there be a system failure?
But, as always, you are very kind. Thank you
User avatar
PeterN
Posts: 366
Joined: Mon Feb 08, 2021 7:56 pm
Location: Krefeld, Germany
Has thanked: 171 times
Been thanked: 203 times
Contact:

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by PeterN »

Did not get a message :-(
Please send me a mail to xxxxxxxxxxxx and I will send again
EDIT: email address removed
User avatar
Fernando Perez
Posts: 378
Joined: Mon Feb 15, 2021 10:09 pm
Location: Santander (Spain)
Has thanked: 195 times
Been thanked: 267 times

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by Fernando Perez »

Peter, received, downloaded and unzipped perfectly.
I'm going to analyze it, but, at a glance, I confirm that with Annex you can do with four lines what requires 100 of Arduino. :D :D
Thanks again.
User avatar
PeterN
Posts: 366
Joined: Mon Feb 08, 2021 7:56 pm
Location: Krefeld, Germany
Has thanked: 171 times
Been thanked: 203 times
Contact:

Re: Alarm clock radio with 303WIFILC01 and RDA5807M

Post by PeterN »

I can confirm this deeply :D

Good luck !
Post Reply