Skip to content

Commit 0fed248

Browse files
authored
FX9630 protocol support, resolves #801 (#805)
New protocol FX9630
1 parent 11c0100 commit 0fed248

File tree

5 files changed

+83
-18
lines changed

5 files changed

+83
-18
lines changed

Multiprotocol/FX_nrf24l01.ino

Lines changed: 78 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -33,29 +33,59 @@ Multiprotocol is distributed in the hope that it will be useful,
3333
#define FX620_PAYLOAD_SIZE 7
3434
#define FX620_CH_OFFSET 1
3535

36+
#define FX9630_PACKET_PERIOD 8124
37+
#define FX9630_BIND_PACKET_PERIOD 8124
38+
#define FX9630_BIND_CHANNEL 51
39+
#define FX9630_PAYLOAD_SIZE 8
40+
#define FX9630_NUM_CHANNELS 3
41+
3642
//#define FORCE_FX620_ID
43+
//#define FORCE_FX9630_ID
3744

3845
static void __attribute__((unused)) FX_send_packet()
3946
{
4047
//Hopp
4148
if(IS_BIND_DONE)
4249
{
4350
XN297_Hopping(hopping_frequency_no++);
44-
hopping_frequency_no &= 0x03;
51+
if(sub_protocol == FX9630)
52+
{
53+
XN297_SetTXAddr(rx_tx_addr, 4);
54+
if (hopping_frequency_no > FX9630_NUM_CHANNELS)
55+
hopping_frequency_no = 0;
56+
}
57+
else // FX816 and FX620
58+
{
59+
hopping_frequency_no &= 0x03;
60+
}
4561
}
4662

4763
memset(packet,0x00,packet_length);
4864

4965
//Channels
50-
uint8_t offset=sub_protocol == FX816 ? FX816_CH_OFFSET:FX620_CH_OFFSET;
51-
uint8_t val=convert_channel_8b(AILERON);
52-
if(val>127+FX_SWITCH)
53-
packet[offset] = sub_protocol == FX816 ? 1:0xFF;
54-
else if(val<127-FX_SWITCH)
55-
packet[offset] = sub_protocol == FX816 ? 2:0x00;
56-
else
57-
packet[offset] = sub_protocol == FX816 ? 0:0x7F;
58-
packet[offset+1] = convert_channel_16b_limit(THROTTLE,0,100); //FX816:0x00..0x63, FX620:0x00..0x5E but that should work
66+
uint8_t val;
67+
if (sub_protocol == FX9630)
68+
{
69+
packet[0] = convert_channel_8b(THROTTLE);
70+
packet[1] = convert_channel_8b(AILERON);
71+
packet[2] = 0xFF - convert_channel_8b(ELEVATOR);
72+
packet[3] = convert_channel_8b(RUDDER);
73+
packet[4] = 0x20;
74+
packet[5] = GET_FLAG(CH5_SW, 0x01); // DR toggle swich: 0 small throw, 1 large throw
75+
packet[5] |= (Channel_data[CH6] < CHANNEL_MIN_COMMAND ? 0x00 : (Channel_data[CH6] > CHANNEL_MAX_COMMAND ? 0x02 : 0x01)) << 1; // Mode A(0) : 6D small throw, B(1) : 6D large throw, C(2) : 3D
76+
}
77+
else // FX816 and FX620
78+
{
79+
uint8_t offset=sub_protocol == FX816 ? FX816_CH_OFFSET:FX620_CH_OFFSET;
80+
val=convert_channel_8b(AILERON);
81+
if(val>127+FX_SWITCH)
82+
packet[offset] = sub_protocol == FX816 ? 1:0xFF;
83+
else if(val<127-FX_SWITCH)
84+
packet[offset] = sub_protocol == FX816 ? 2:0x00;
85+
else
86+
packet[offset] = sub_protocol == FX816 ? 0:0x7F;
87+
packet[offset+1] = convert_channel_16b_limit(THROTTLE,0,100); //FX816:0x00..0x63, FX620:0x00..0x5E but that should work
88+
}
5989

6090
//Bind and specifics
6191
if(sub_protocol == FX816)
@@ -67,7 +97,7 @@ static void __attribute__((unused)) FX_send_packet()
6797
packet[1] = rx_tx_addr[0];
6898
packet[2] = rx_tx_addr[1];
6999
}
70-
else //FX620
100+
else if(sub_protocol == FX620)
71101
{
72102
if(IS_BIND_IN_PROGRESS)
73103
{
@@ -82,12 +112,27 @@ static void __attribute__((unused)) FX_send_packet()
82112
packet[5] = 0xAB; // Is it based on ID??
83113
}
84114
}
115+
else // FX9630
116+
{
117+
if(IS_BIND_IN_PROGRESS)
118+
{
119+
memcpy(packet,rx_tx_addr, 4);
120+
packet[4] = hopping_frequency[1];
121+
packet[5] = hopping_frequency[2];
122+
packet[7] = 0x55;
123+
}
124+
}
85125

86126
//Check
127+
uint8_t last_packet_idx = packet_length-1;
128+
if (sub_protocol == FX9630 && IS_BIND_IN_PROGRESS)
129+
last_packet_idx--;
87130
val=0;
88-
for(uint8_t i=0;i<packet_length-1;i++)
131+
for(uint8_t i=0;i<last_packet_idx;i++)
89132
val+=packet[i];
90-
packet[packet_length-1]=val;
133+
if (sub_protocol == FX9630)
134+
val = val ^ 0xFF;
135+
packet[last_packet_idx]=val;
91136

92137
//Debug
93138
#if 0
@@ -112,13 +157,20 @@ static void __attribute__((unused)) FX_RF_init()
112157
packet_period = FX816_PACKET_PERIOD;
113158
packet_length = FX816_PAYLOAD_SIZE;
114159
}
115-
else //FX620
160+
else if(sub_protocol == FX620)
116161
{
117162
XN297_SetTXAddr((uint8_t *)"\xaa\xbb\xcc", 3);
118163
XN297_RFChannel(FX620_BIND_CHANNEL);
119164
packet_period = FX620_BIND_PACKET_PERIOD;
120165
packet_length = FX620_PAYLOAD_SIZE;
121166
}
167+
else // FX9630
168+
{
169+
XN297_SetTXAddr((uint8_t *)"\x56\x78\x90\x12", 4);
170+
XN297_RFChannel(FX9630_BIND_CHANNEL);
171+
packet_period = FX9630_BIND_PACKET_PERIOD;
172+
packet_length = FX9630_PAYLOAD_SIZE;
173+
}
122174
}
123175

124176
static void __attribute__((unused)) FX_initialize_txid()
@@ -133,7 +185,7 @@ static void __attribute__((unused)) FX_initialize_txid()
133185
for(uint8_t i=0;i<FX_NUM_CHANNELS;i++)
134186
hopping_frequency[i]+=rx_tx_addr[3]&0x07;
135187
}
136-
else//FX620
188+
else if(sub_protocol == FX620)
137189
{
138190
rx_tx_addr[0] = rx_tx_addr[3];
139191
hopping_frequency[0] = 0x18 + rx_tx_addr[3]&0x07; // just to try something
@@ -144,6 +196,17 @@ static void __attribute__((unused)) FX_initialize_txid()
144196
for(uint8_t i=1;i<FX_NUM_CHANNELS;i++)
145197
hopping_frequency[i] = i*10 + hopping_frequency[0];
146198
}
199+
else // FX9630
200+
{
201+
#ifdef FORCE_FX9630_ID
202+
memcpy(rx_tx_addr,(uint8_t*)"\xCE\x31\x9B\x73", 4);
203+
memcpy(hopping_frequency,"\x13\x1A\x38", FX9630_NUM_CHANNELS); //Original dump=19=0x13,26=0x1A,56=0x38
204+
#else
205+
hopping_frequency[0] = 0x13; // constant
206+
hopping_frequency[1] = RX_num & 0x0F + 0x1A;
207+
hopping_frequency[2] = rx_tx_addr[3] & 0x0F + 0x38;
208+
#endif
209+
}
147210
}
148211

149212
uint16_t FX_callback()

Multiprotocol/Multi.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@
5555
55,Frsky_RX,Multi,CloneTX,EraseTX,CPPM
5656
56,AFHDS2A_RX,Multi,CPPM
5757
57,HoTT,Sync,No_Sync
58-
58,FX,816,620
58+
58,FX,816,620,9630
5959
59,Bayang_RX,Multi,CPPM
6060
60,Pelikan,Pro,Lite,SCX24
6161
61,Tiger

Multiprotocol/Multi_Protos.ino

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -173,7 +173,7 @@ const char STR_SUBTYPE_JJRC345[] = "\x08""JJRC345\0""SkyTmblr";
173173
const char STR_SUBTYPE_MOULKG[] = "\x06""Analog""Digit\0";
174174
const char STR_SUBTYPE_KF606[] = "\x06""KF606\0""MIG320""ZCZ50\0";
175175
const char STR_SUBTYPE_E129[] = "\x04""E129""C186";
176-
const char STR_SUBTYPE_FX[] = "\x03""816""620";
176+
const char STR_SUBTYPE_FX[] = "\x04""816\0""620\0""9630";
177177
#define NO_SUBTYPE nullptr
178178

179179
#ifdef SEND_CPPM
@@ -315,7 +315,7 @@ const mm_protocol_definition multi_protocols[] = {
315315
{PROTO_FUTABA, STR_FUTABA, STR_SUBTYPE_FUTABA, 1, OPTION_RFTUNE, 1, 1, SW_CC2500, SFHSS_init, SFHSS_callback },
316316
#endif
317317
#if defined(FX_NRF24L01_INO)
318-
{PROTO_FX, STR_FX, STR_SUBTYPE_FX, 2, OPTION_NONE, 0, 0, SW_NRF, FX_init, FX_callback },
318+
{PROTO_FX, STR_FX, STR_SUBTYPE_FX, 3, OPTION_NONE, 0, 0, SW_NRF, FX_init, FX_callback },
319319
#endif
320320
#if defined(FY326_NRF24L01_INO)
321321
{PROTO_FY326, STR_FY326, STR_SUBTYPE_FY326, 2, OPTION_NONE, 0, 0, SW_NRF, FY326_init, FY326_callback },

Multiprotocol/Multiprotocol.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -461,6 +461,7 @@ enum FX
461461
{
462462
FX816 = 0,
463463
FX620 = 1,
464+
FX9630 = 2,
464465
};
465466

466467
#define NONE 0

Multiprotocol/_Config.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -670,6 +670,7 @@ const PPM_Parameters PPM_prot[14*NBR_BANKS]= {
670670
PROTO_FX
671671
FX816
672672
FX620
673+
FX9630
673674
PROTO_FY326
674675
FY326
675676
FY319

0 commit comments

Comments
 (0)