├── .gitattributes
├── .gitignore
├── README.md
├── examples
├── README.md
└── Si4703_Radio_Test
│ └── Si4703_Radio_Test.ino
├── keywords.txt
├── library.properties
└── src
├── README.md
├── SparkFunSi4703.cpp
├── SparkFunSi4703.h
└── Standard_code_header.c
/.gitattributes:
--------------------------------------------------------------------------------
1 | # Auto detect text files and perform LF normalization
2 | * text=auto
3 |
4 | # Custom for Visual Studio
5 | *.cs diff=csharp
6 | *.sln merge=union
7 | *.csproj merge=union
8 | *.vbproj merge=union
9 | *.fsproj merge=union
10 | *.dbproj merge=union
11 |
12 | # Standard to msysgit
13 | *.doc diff=astextplain
14 | *.DOC diff=astextplain
15 | *.docx diff=astextplain
16 | *.DOCX diff=astextplain
17 | *.dot diff=astextplain
18 | *.DOT diff=astextplain
19 | *.pdf diff=astextplain
20 | *.PDF diff=astextplain
21 | *.rtf diff=astextplain
22 | *.RTF diff=astextplain
23 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | #################
2 | ## SparkFun Useful stuff
3 | #################
4 |
5 | ## AVR Development
6 | *.eep
7 | *.elf
8 | *.lst
9 | *.lss
10 | *.sym
11 | *.d
12 | *.o
13 | *.srec
14 | *.map
15 |
16 | ## Notepad++ backup files
17 | *.bak
18 |
19 | ## BOM files
20 | *bom*
21 |
22 | #################
23 | ## Eclipse
24 | #################
25 |
26 | *.pydevproject
27 | .project
28 | .metadata
29 | bin/
30 | tmp/
31 | *.tmp
32 | *.bak
33 | *.swp
34 | *~.nib
35 | local.properties
36 | .classpath
37 | .settings/
38 | .loadpath
39 |
40 | # External tool builders
41 | .externalToolBuilders/
42 |
43 | # Locally stored "Eclipse launch configurations"
44 | *.launch
45 |
46 | # CDT-specific
47 | .cproject
48 |
49 | # PDT-specific
50 | .buildpath
51 |
52 |
53 | #############
54 | ## Eagle
55 | #############
56 |
57 | # Ignore the board and schematic backup files
58 | *.b#?
59 | *.s#?
60 |
61 |
62 | #################
63 | ## Visual Studio
64 | #################
65 |
66 | ## Ignore Visual Studio temporary files, build results, and
67 | ## files generated by popular Visual Studio add-ons.
68 |
69 | # User-specific files
70 | *.suo
71 | *.user
72 | *.sln.docstates
73 |
74 | # Build results
75 | [Dd]ebug/
76 | [Rr]elease/
77 | *_i.c
78 | *_p.c
79 | *.ilk
80 | *.meta
81 | *.obj
82 | *.pch
83 | *.pdb
84 | *.pgc
85 | *.pgd
86 | *.rsp
87 | *.sbr
88 | *.tlb
89 | *.tli
90 | *.tlh
91 | *.tmp
92 | *.vspscc
93 | .builds
94 | *.dotCover
95 |
96 | ## TODO: If you have NuGet Package Restore enabled, uncomment this
97 | #packages/
98 |
99 | # Visual C++ cache files
100 | ipch/
101 | *.aps
102 | *.ncb
103 | *.opensdf
104 | *.sdf
105 |
106 | # Visual Studio profiler
107 | *.psess
108 | *.vsp
109 |
110 | # ReSharper is a .NET coding add-in
111 | _ReSharper*
112 |
113 | # Installshield output folder
114 | [Ee]xpress
115 |
116 | # DocProject is a documentation generator add-in
117 | DocProject/buildhelp/
118 | DocProject/Help/*.HxT
119 | DocProject/Help/*.HxC
120 | DocProject/Help/*.hhc
121 | DocProject/Help/*.hhk
122 | DocProject/Help/*.hhp
123 | DocProject/Help/Html2
124 | DocProject/Help/html
125 |
126 | # Click-Once directory
127 | publish
128 |
129 | # Others
130 | [Bb]in
131 | [Oo]bj
132 | sql
133 | TestResults
134 | *.Cache
135 | ClientBin
136 | stylecop.*
137 | ~$*
138 | *.dbmdl
139 | Generated_Code #added for RIA/Silverlight projects
140 |
141 | # Backup & report files from converting an old project file to a newer
142 | # Visual Studio version. Backup files are not needed, because we have git ;-)
143 | _UpgradeReport_Files/
144 | Backup*/
145 | UpgradeLog*.XML
146 |
147 |
148 | ############
149 | ## Windows
150 | ############
151 |
152 | # Windows image file caches
153 | Thumbs.db
154 |
155 | # Folder config file
156 | Desktop.ini
157 |
158 |
159 | #############
160 | ## Python
161 | #############
162 |
163 | *.py[co]
164 |
165 | # Packages
166 | *.egg
167 | *.egg-info
168 | dist
169 | build
170 | eggs
171 | parts
172 | bin
173 | var
174 | sdist
175 | develop-eggs
176 | .installed.cfg
177 |
178 | # Installer logs
179 | pip-log.txt
180 |
181 | # Unit test / coverage reports
182 | .coverage
183 | .tox
184 |
185 | #Translations
186 | *.mo
187 |
188 | #Mr Developer
189 | .mr.developer.cfg
190 |
191 | # Mac crap
192 | .DS_Store
193 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | SparkFun Si4703 Arduino Library
2 | ========================================
3 |
4 |
5 |
6 |  |
7 |  |
8 |
9 |
10 | SparkFun Si4703 Breakout [BOB-11083] |
11 | SparkFun FM Tuner Evaluation Board - Si4703 [WRL-12938] |
12 |
13 |
14 |
15 |
16 | Basic functionality of the Si4703 FM tuner chip. Allows user to tune to different FM stations, find station ID and song name, and RDS and RBDS information.
17 |
18 | Repository Contents
19 | -------------------
20 |
21 | * **/examples** - Example sketches for the library (.ino). Run these from the Arduino IDE.
22 | * **/src** - Source files for the library (.cpp, .h).
23 | * **keywords.txt** - Keywords from this library that will be highlighted in the Arduino IDE.
24 | * **library.properties** - General library properties for the Arduino package manager.
25 |
26 | Documentation
27 | --------------
28 |
29 | * **[Installing an Arduino Library Guide](https://learn.sparkfun.com/tutorials/installing-an-arduino-library)** - Basic information on how to install an Arduino library.
30 | * **[Hookup Guide](https://learn.sparkfun.com/tutorials/si4703-fm-radio-receiver-hookup-guide)** - Basic hookup Guide for the SI4703 Evaluation board.
31 | * **[Product Repository](https://github.com/sparkfun/FM_Tuner_Basic_Breakout-Si4703)** - Main repository (including hardware files) for the Si4703 Breakout.
32 |
33 | Products that use this Library
34 | ---------------------------------
35 | * [SparkFun FM Tuner Evaluation Board](https://www.sparkfun.com/products/10663)- Evaluation board for Si4703. Includes audio jack.
36 | * [SparkFun FM Tuner Basic Breakout](https://www.sparkfun.com/products/11083)- Basic breakout of Si4703.
37 |
38 | License Information
39 | -------------------
40 |
41 | This product is _**open source**_!
42 |
43 | Distributed as-is; no warranty is given.
44 |
45 | - Your friends at SparkFun.
46 |
47 | _The original SparkFun code was modified by Simon Monk. Thanks Simon!_
48 |
--------------------------------------------------------------------------------
/examples/README.md:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sparkfun/SparkFun_Si4703_Arduino_Library/2510e57738ef3fb0c938d5d7283dc99060ae606d/examples/README.md
--------------------------------------------------------------------------------
/examples/Si4703_Radio_Test/Si4703_Radio_Test.ino:
--------------------------------------------------------------------------------
1 | #include
2 | #include
3 |
4 | int resetPin = 2;
5 | int SDIO = A4;
6 | int SCLK = A5;
7 | int STC = 3;
8 |
9 | Si4703_Breakout radio(resetPin, SDIO, SCLK, STC);
10 | int channel;
11 | int volume;
12 | char rdsBuffer[10];
13 |
14 | void setup()
15 | {
16 | Serial.begin(9600);
17 | Serial.println("\n\nSi4703_Breakout Test Sketch");
18 | Serial.println("===========================");
19 | Serial.println("a b Favourite stations");
20 | Serial.println("+ - Volume (max 15)");
21 | Serial.println("u d Seek up / down");
22 | Serial.println("r Listen for RDS Data (15 sec timeout)");
23 | Serial.println("Send me a command letter.");
24 |
25 |
26 | radio.powerOn();
27 | radio.setVolume(0);
28 | }
29 |
30 | void loop()
31 | {
32 | if (Serial.available())
33 | {
34 | char ch = Serial.read();
35 | if (ch == 'u')
36 | {
37 | channel = radio.seekUp();
38 | displayInfo();
39 | }
40 | else if (ch == 'd')
41 | {
42 | channel = radio.seekDown();
43 | displayInfo();
44 | }
45 | else if (ch == '+')
46 | {
47 | volume ++;
48 | if (volume == 16) volume = 15;
49 | radio.setVolume(volume);
50 | displayInfo();
51 | }
52 | else if (ch == '-')
53 | {
54 | volume --;
55 | if (volume < 0) volume = 0;
56 | radio.setVolume(volume);
57 | displayInfo();
58 | }
59 | else if (ch == 'a')
60 | {
61 | channel = 930; // Rock FM
62 | radio.setChannel(channel);
63 | displayInfo();
64 | }
65 | else if (ch == 'b')
66 | {
67 | channel = 974; // BBC R4
68 | radio.setChannel(channel);
69 | displayInfo();
70 | }
71 | else if (ch == 'r')
72 | {
73 | Serial.println("RDS listening");
74 | radio.readRDS(rdsBuffer, 15000);
75 | Serial.print("RDS heard:");
76 | Serial.println(rdsBuffer);
77 | }
78 | }
79 | }
80 |
81 | void displayInfo()
82 | {
83 | Serial.print("Channel:"); Serial.print(channel);
84 | Serial.print(" Volume:"); Serial.println(volume);
85 | }
86 |
--------------------------------------------------------------------------------
/keywords.txt:
--------------------------------------------------------------------------------
1 | #######################################
2 | # Syntax Coloring Map For Si4703
3 | #######################################
4 |
5 | #######################################
6 | # Datatypes (KEYWORD1)
7 | #######################################
8 | Si4703_Breakout KEYWORD1
9 |
10 | #######################################
11 | # Methods and Functions (KEYWORD2)
12 | #######################################
13 | powerOn KEYWORD2
14 | setChannel KEYWORD2
15 | seekUp KEYWORD2
16 | seekDown KEYWORD2
17 | setVolume KEYWORD2
18 | readRDS KEYWORD2
--------------------------------------------------------------------------------
/library.properties:
--------------------------------------------------------------------------------
1 | name=SparkFun Si4703
2 | version=1.3.0
3 | author=Simon Monk, SparkFun Electronics
4 | maintainer=SparkFun Electronics
5 | sentence=Basic functionality of the Si4703 FM tuner chip.
6 | paragraph=Allows user to tune to different FM stations, find station ID and song name, and RDS and RBDS information.
7 | category=Other
8 | url=https://github.com/sparkfun/SparkFun_Si4703_Arduino_Library
9 | architectures=*
10 |
--------------------------------------------------------------------------------
/src/README.md:
--------------------------------------------------------------------------------
1 | This folder should contain the .cpp and .h files for the library.
2 |
3 | If backward compatibility is needed, source code should be placed in the library root folder and in a "utilyt" folder.
4 |
5 | Check out the [library specification](https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5:-Library-specification) for more details.
--------------------------------------------------------------------------------
/src/SparkFunSi4703.cpp:
--------------------------------------------------------------------------------
1 | #include "Arduino.h"
2 | #include "SparkFunSi4703.h"
3 | #include "Wire.h"
4 |
5 | Si4703_Breakout::Si4703_Breakout(int resetPin, int sdioPin, int sclkPin, int stcIntPin)
6 | {
7 | _resetPin = resetPin;
8 | _sdioPin = sdioPin;
9 | _sclkPin = sclkPin;
10 | _stcIntPin = stcIntPin;
11 | }
12 |
13 | void Si4703_Breakout::powerOn()
14 | {
15 | si4703_init();
16 | }
17 |
18 | void Si4703_Breakout::setChannel(int channel)
19 | {
20 | //Freq(MHz) = 0.200(in USA) * Channel + 87.5MHz
21 | //97.3 = 0.2 * Chan + 87.5
22 | //9.8 / 0.2 = 49
23 | int newChannel = channel * 10; //973 * 10 = 9730
24 | newChannel -= 8750; //9730 - 8750 = 980
25 | newChannel /= 10; //980 / 10 = 98
26 |
27 | //These steps come from AN230 page 20 rev 0.5
28 | readRegisters();
29 | si4703_registers[CHANNEL] &= 0xFE00; //Clear out the channel bits
30 | si4703_registers[CHANNEL] |= newChannel; //Mask in the new channel
31 | si4703_registers[CHANNEL] |= (1< 15) volume = 15;
64 | si4703_registers[SYSCONFIG2] &= 0xFFF0; //Clear volume bits
65 | si4703_registers[SYSCONFIG2] |= volume; //Set new volume
66 | updateRegisters(); //Update
67 | }
68 |
69 | void Si4703_Breakout::readRDS(char* buffer, long timeout)
70 | {
71 | long endTime = millis() + timeout;
72 | boolean completed[] = {false, false, false, false};
73 | int completedCount = 0;
74 | while(completedCount < 4 && millis() < endTime) {
75 | readRegisters();
76 | if(si4703_registers[STATUSRSSI] & (1<> 8;
87 | char Dl = (si4703_registers[RDSD] & 0x00FF);
88 | buffer[index * 2] = Dh;
89 | buffer[index * 2 +1] = Dl;
90 | // Serial.print(si4703_registers[RDSD]); Serial.print(" ");
91 | // Serial.print(index);Serial.print(" ");
92 | // Serial.write(Dh);
93 | // Serial.write(Dl);
94 | // Serial.println();
95 | }
96 | delay(40); //Wait for the RDS bit to clear
97 | }
98 | else {
99 | delay(30); //From AN230, using the polling method 40ms should be sufficient amount of time between checks
100 | }
101 | }
102 | if (millis() >= endTime) {
103 | buffer[0] ='\0';
104 | return;
105 | }
106 |
107 | buffer[8] = '\0';
108 | }
109 |
110 |
111 |
112 |
113 | //To get the Si4703 inito 2-wire mode, SEN needs to be high and SDIO needs to be low after a reset
114 | //The breakout board has SEN pulled high, but also has SDIO pulled high. Therefore, after a normal power up
115 | //The Si4703 will be in an unknown state. RST must be controlled
116 | void Si4703_Breakout::si4703_init()
117 | {
118 | pinMode(_resetPin, OUTPUT);
119 | pinMode(_sdioPin, OUTPUT); //SDIO is connected to A4 for I2C
120 | pinMode(_stcIntPin, OUTPUT); //STC (search/tune complete) interrupt pin
121 | digitalWrite(_sdioPin, LOW); //A low SDIO indicates a 2-wire interface
122 | digitalWrite(_resetPin, LOW); //Put Si4703 into reset
123 | digitalWrite(_stcIntPin, HIGH); //STC goes low on interrupt
124 | delay(1); //Some delays while we allow pins to settle
125 | digitalWrite(_resetPin, HIGH); //Bring Si4703 out of reset with SDIO set to low and SEN pulled high with on-board resistor
126 | delay(1); //Allow Si4703 to come out of reset
127 |
128 | Wire.begin(); //Now that the unit is reset and I2C inteface mode, we need to begin I2C
129 |
130 | readRegisters(); //Read the current register set
131 | //si4703_registers[0x07] = 0xBC04; //Enable the oscillator, from AN230 page 9, rev 0.5 (DOES NOT WORK, wtf Silicon Labs datasheet?)
132 | si4703_registers[0x07] = 0x8100; //Enable the oscillator, from AN230 page 9, rev 0.61 (works)
133 | si4703_registers[0x04] |= 0x2000; //Set bit 14 to high to enable STC Interrupt on GPIO2
134 | updateRegisters(); //Update
135 |
136 | delay(500); //Wait for clock to settle - from AN230 page 9
137 |
138 | readRegisters(); //Read the current register set
139 | si4703_registers[POWERCFG] = 0x4001; //Enable the IC
140 | // si4703_registers[POWERCFG] |= (1<> 8;
179 | byte low_byte = si4703_registers[regSpot] & 0x00FF;
180 |
181 | Wire.write(high_byte); //Upper 8 bits
182 | Wire.write(low_byte); //Lower 8 bits
183 | }
184 |
185 | //End this transmission
186 | byte ack = Wire.endTransmission();
187 | if(ack != 0) { //We have a problem!
188 | return(FAIL);
189 | }
190 |
191 | return(SUCCESS);
192 | }
193 |
194 | //Seeks out the next available station
195 | //Returns the freq if it made it
196 | //Returns zero if failed
197 | int Si4703_Breakout::seek(byte seekDirection){
198 | readRegisters();
199 | //Set seek mode wrap bit
200 | si4703_registers[POWERCFG] |= (1<
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 | Resources:
13 |
14 |
15 | Development environment specifics:
16 |
17 |
18 |
19 |
20 | This code is beerware; if you see me (or any other SparkFun employee) at the
21 | local, and you've found our code helpful, please buy us a round!
22 |
23 | Distributed as-is; no warranty is given.
24 | ******************************************************************************/
--------------------------------------------------------------------------------