sync decode sdk to android-example

This commit is contained in:
strawmanbobi
2025-10-18 17:55:40 +08:00
parent 3e3e15eb46
commit b3f8ae0785
7 changed files with 140 additions and 49 deletions

View File

@@ -54,7 +54,7 @@ JNIEXPORT jint JNICALL Java_net_irext_decode_sdk_IRDecode_irOpenBinary
(*env)->ReleaseByteArrayElements(env, binaries, j_buffer, JNI_ABORT); (*env)->ReleaseByteArrayElements(env, binaries, j_buffer, JNI_ABORT);
return IR_DECODE_FAILED; return IR_DECODE_FAILED;
} }
(*env)->ReleaseByteArrayElements(env, binaries, j_buffer, JNI_ABORT);
return IR_DECODE_SUCCEEDED; return IR_DECODE_SUCCEEDED;
} }

View File

@@ -126,30 +126,30 @@ typedef enum
AC_APPLY_MAX AC_APPLY_MAX
} t_ac_apply; } t_ac_apply;
typedef struct _ac_hex typedef struct ac_hex
{ {
UINT8 len; UINT8 len;
UINT8 *data; UINT8 *data;
} t_ac_hex; } t_ac_hex;
typedef struct _ac_level typedef struct ac_level
{ {
UINT16 low; UINT16 low;
UINT16 high; UINT16 high;
} t_ac_level; } t_ac_level;
typedef struct _ac_bootcode typedef struct ac_bootcode
{ {
UINT16 len; UINT16 len;
UINT16 data[16]; UINT16 data[16];
} t_ac_bootcode; } t_ac_boot_code;
typedef struct _ac_delaycode typedef struct ac_delay_code
{ {
INT16 pos; INT16 pos;
UINT16 time[8]; UINT16 time[8];
UINT16 time_cnt; UINT16 time_cnt;
} t_ac_delaycode; } t_ac_delay_code;
/* /*
* the array of tag_100X application data * the array of tag_100X application data
@@ -157,26 +157,26 @@ typedef struct _ac_delaycode
* byte_pos : the position of update byte * byte_pos : the position of update byte
* byte_value : the value to be updated to position * byte_value : the value to be updated to position
*/ */
typedef struct _tag_comp_type_1 typedef struct tag_comp_type_1
{ {
UINT8 seg_len; UINT8 seg_len;
UINT8 *segment; UINT8 *segment;
} t_tag_comp; } t_tag_comp;
typedef struct _tag_swing_info typedef struct tag_swing_info
{ {
swing_type type; swing_type type;
UINT8 mode_count; UINT8 mode_count;
UINT8 dir_index; UINT8 dir_index;
} t_swing_info; } t_swing_info;
typedef struct _tag_power_1 typedef struct tag_power_1
{ {
UINT8 len; UINT8 len;
t_tag_comp comp_data[AC_POWER_MAX]; t_tag_comp comp_data[AC_POWER_MAX];
} t_power_1; } t_power_1;
typedef struct _tag_temp_1 typedef struct tag_temp_1
{ {
UINT8 len; UINT8 len;
UINT8 type; UINT8 type;
@@ -236,7 +236,7 @@ typedef struct tag_horiswing_1
} hori_swing_1; } hori_swing_1;
#endif #endif
typedef struct _tag_checksum_data typedef struct tag_checksum_data
{ {
UINT8 len; UINT8 len;
UINT8 type; UINT8 type;
@@ -273,7 +273,7 @@ typedef struct tag_solo_code
UINT8 solo_function_codes[AC_FUNCTION_MAX - 1]; UINT8 solo_function_codes[AC_FUNCTION_MAX - 1];
} t_solo_code; } t_solo_code;
typedef struct _ac_bitnum typedef struct ac_bitnum
{ {
INT16 pos; INT16 pos;
UINT16 bits; UINT16 bits;
@@ -302,7 +302,7 @@ typedef enum
CHECKSUM_TYPE_MAX, CHECKSUM_TYPE_MAX,
} t_checksum_type; } t_checksum_type;
typedef struct _ac_n_mode_info typedef struct ac_n_mode_info
{ {
UINT8 enable; UINT8 enable;
UINT8 all_speed; UINT8 all_speed;
@@ -320,8 +320,8 @@ typedef struct ac_protocol
t_ac_hex default_code; t_ac_hex default_code;
t_ac_level zero; t_ac_level zero;
t_ac_level one; t_ac_level one;
t_ac_bootcode boot_code; t_ac_boot_code boot_code;
t_ac_delaycode dc[MAX_DELAYCODE_NUM]; t_ac_delay_code dc[MAX_DELAYCODE_NUM];
t_power_1 power1; t_power_1 power1;
t_temp_1 temp1; t_temp_1 temp1;
t_mode_1 mode1; t_mode_1 mode1;

View File

@@ -12,6 +12,8 @@ Revision log:
#ifndef _IR_DEFS_H #ifndef _IR_DEFS_H
#define _IR_DEFS_H #define _IR_DEFS_H
#define IR_DECODE_LIB_VER "1.5.0"
#if defined (BOARD_PC) #if defined (BOARD_PC)
#pragma ide diagnostic ignored "OCUnusedGlobalDeclarationInspection" #pragma ide diagnostic ignored "OCUnusedGlobalDeclarationInspection"
#pragma ide diagnostic ignored "OCUnusedMacroInspection" #pragma ide diagnostic ignored "OCUnusedMacroInspection"
@@ -65,7 +67,7 @@ void noprint(const char *fmt, ...);
#define ir_memset(A, B, C) memset(A, B, C) #define ir_memset(A, B, C) memset(A, B, C)
#define ir_strlen(A) strlen(A) #define ir_strlen(A) strlen(A)
#if ((defined BOARD_PC) || (defined BOARD_PC_JNI)) && (defined DEBUG) #if ((defined BOARD_PC) || (defined BOARD_PC_JNI)) && (defined DEBUG)
#define ir_printf printf #define ir_printf(...) do { printf(__VA_ARGS__); fflush(stdout); } while(0)
#else #else
#define ir_printf noprint #define ir_printf noprint
#endif #endif

View File

@@ -22,7 +22,7 @@ Revision log:
struct ir_bin_buffer binary_file; struct ir_bin_buffer binary_file;
struct ir_bin_buffer *p_ir_buffer = &binary_file; struct ir_bin_buffer *p_ir_buffer = &binary_file;
static const char* version = "0.2.5"; static const char* version = IR_DECODE_LIB_VER;
#if defined USE_DYNAMIC_TAG #if defined USE_DYNAMIC_TAG
struct tag_head *tags; struct tag_head *tags;
@@ -82,6 +82,7 @@ static INT8 ir_ac_binary_open(UINT8 *binary, UINT16 bin_length);
static UINT16 ir_ac_control(t_remote_ac_status ac_status, UINT16* user_data, UINT8 key_code, static UINT16 ir_ac_control(t_remote_ac_status ac_status, UINT16* user_data, UINT8 key_code,
BOOL change_wind_direction); BOOL change_wind_direction);
static INT8 ir_ac_binary_close(); static INT8 ir_ac_binary_close();
static BOOL validate_ac_status(t_remote_ac_status* ac_status, BOOL change_wind_dir);
#if !defined NO_FS #if !defined NO_FS
static INT8 ir_tv_file_open(const char *file_name); static INT8 ir_tv_file_open(const char *file_name);
@@ -218,7 +219,19 @@ INT8 ir_binary_open(const UINT8 category, const UINT8 sub_category, UINT8* binar
return IR_DECODE_FAILED; return IR_DECODE_FAILED;
} }
ret = ir_tv_binary_open(binary, bin_length); #if (defined(BOARD_PC) || defined (BOARD_PC_DLL) || defined (BOARD_ANDROID))
binary_content = (UINT8 *) ir_malloc(bin_length);
if (NULL == binary_content)
{
ir_printf("failed to malloc memory for binary\n");
return IR_DECODE_FAILED;
}
memcpy(binary_content, binary, bin_length);
#else
binary_content = binary;
#endif
ret = ir_tv_binary_open(binary_content, bin_length);
if (IR_DECODE_SUCCEEDED == ret) if (IR_DECODE_SUCCEEDED == ret)
{ {
return ir_tv_binary_parse(ir_hexadecimal); return ir_tv_binary_parse(ir_hexadecimal);
@@ -259,6 +272,10 @@ UINT16 ir_decode(UINT8 key_code, UINT16* user_data,
ac_status->ac_temp, ac_status->ac_wind_dir, ac_status->ac_temp, ac_status->ac_wind_dir,
ac_status->ac_wind_speed, ac_status->ac_wind_speed,
key_code, change_wind_direction); key_code, change_wind_direction);
// ac status validation
if (FALSE == validate_ac_status(ac_status, change_wind_direction)) {
return 0;
}
return ir_ac_control(*ac_status, user_data, key_code, change_wind_direction); return ir_ac_control(*ac_status, user_data, key_code, change_wind_direction);
} }
} }
@@ -489,6 +506,35 @@ static INT8 ir_ac_binary_close()
return IR_DECODE_SUCCEEDED; return IR_DECODE_SUCCEEDED;
} }
static BOOL validate_ac_status(t_remote_ac_status* ac_status, BOOL change_wind_dir)
{
if (AC_POWER_OFF != ac_status->ac_power && AC_POWER_ON != ac_status->ac_power)
{
return FALSE;
}
if (ac_status->ac_mode < AC_MODE_COOL || ac_status->ac_mode >= AC_MODE_MAX)
{
return FALSE;
}
if (ac_status->ac_temp < AC_TEMP_16 || ac_status->ac_temp >= AC_TEMP_MAX)
{
return FALSE;
}
if (ac_status->ac_wind_speed < AC_WS_AUTO || ac_status->ac_wind_speed >= AC_WS_MAX)
{
return FALSE;
}
if (ac_status->ac_wind_dir < AC_SWING_ON || ac_status->ac_wind_dir >= AC_SWING_MAX)
{
return FALSE;
}
if (0 != change_wind_dir && 1 != change_wind_dir)
{
return FALSE;
}
return TRUE;
}
// utils // utils
INT8 get_temperature_range(UINT8 ac_mode, INT8 *temp_min, INT8 *temp_max) INT8 get_temperature_range(UINT8 ac_mode, INT8 *temp_min, INT8 *temp_max)
{ {
@@ -652,7 +698,7 @@ static INT8 ir_tv_file_open(const char *file_name)
if (stream == NULL) if (stream == NULL)
{ {
ir_printf("\nfile open failed\n"); ir_printf("file open failed\n");
return IR_DECODE_FAILED; return IR_DECODE_FAILED;
} }
@@ -662,7 +708,7 @@ static INT8 ir_tv_file_open(const char *file_name)
binary_content = (UINT8 *) ir_malloc(binary_length); binary_content = (UINT8 *) ir_malloc(binary_length);
if (NULL == binary_content) if (NULL == binary_content)
{ {
ir_printf("\nfailed to alloc memory for binary\n"); ir_printf("failed to malloc memory for binary\n");
fclose(stream); fclose(stream);
return IR_DECODE_FAILED; return IR_DECODE_FAILED;
} }
@@ -681,6 +727,7 @@ static INT8 ir_tv_file_open(const char *file_name)
if (IR_DECODE_FAILED == ir_tv_binary_open(binary_content, (UINT16) binary_length)) if (IR_DECODE_FAILED == ir_tv_binary_open(binary_content, (UINT16) binary_length))
{ {
ir_printf("failed to parse command type binary\n");
ir_free(binary_content); ir_free(binary_content);
binary_length = 0; binary_length = 0;
return IR_DECODE_FAILED; return IR_DECODE_FAILED;

View File

@@ -30,14 +30,20 @@ void input_number(int *val)
char n[50]={0}; char n[50]={0};
int i = 0; int i = 0;
*val = 0; *val = 0;
scanf("%s", n); if (0 != scanf("%s", n))
{
return;
}
getchar(); getchar();
while(1) while(1)
{ {
if(n[i] < '0'||n[i] > '9') if(n[i] < '0'||n[i] > '9')
{ {
printf("\nInvalid number format, please re-input : "); printf("invalid number format, please re-input : ");
scanf("%s", n); if (0 != scanf("%s", n))
{
break;
}
i=0; i=0;
} }
else else
@@ -94,13 +100,13 @@ static INT8 decode_as_ac(char *file_name)
{ {
if (1 == first_time) if (1 == first_time)
{ {
printf("Please input valid key code " printf("please input valid key code "
"(Key code could be referenced from https://irext.net/doc#keymap) : \n"); "(key code could be referenced from https://irext.net/doc#keymap) : \n");
first_time = 0; first_time = 0;
} }
else else
{ {
printf("Please input valid key code : \n"); printf("please input valid key code : \n");
} }
input_number(&key_code); input_number(&key_code);
@@ -219,7 +225,7 @@ static INT8 decode_as_ac(char *file_name)
ac_status.ac_wind_dir, ac_status.ac_wind_dir,
key_code); key_code);
length = ir_decode(key_code, user_data, &ac_status, change_wind_dir); length = ir_decode(key_code, user_data, &ac_status, change_wind_dir);
printf("\n === Binary decoded : %d\n", length); printf("\n === binary decoded : %d\n", length);
for (index = 0; index < length; index++) for (index = 0; index < length; index++)
{ {
printf("%d, ", user_data[index]); printf("%d, ", user_data[index]);
@@ -245,6 +251,7 @@ static INT8 decode_as_tv(char *file_name, UINT8 ir_hex_encode)
// here remote category TV represents for command typed IR code // here remote category TV represents for command typed IR code
if (IR_DECODE_FAILED == ir_file_open(REMOTE_CATEGORY_TV, ir_hex_encode, file_name)) if (IR_DECODE_FAILED == ir_file_open(REMOTE_CATEGORY_TV, ir_hex_encode, file_name))
{ {
printf("failed to open file : %s\n", file_name);
ir_close(); ir_close();
return IR_DECODE_FAILED; return IR_DECODE_FAILED;
} }
@@ -253,13 +260,13 @@ static INT8 decode_as_tv(char *file_name, UINT8 ir_hex_encode)
{ {
if (1 == first_time) if (1 == first_time)
{ {
printf("Please input valid key code " printf("please input valid key code "
"(Key code could be referenced from https://irext.net/doc#keymap) : \n"); "(Key code could be referenced from https://irext.net/doc#keymap) : \n");
first_time = 0; first_time = 0;
} }
else else
{ {
printf("Please input valid key code : \n"); printf("please input valid key code : \n");
} }
input_number(&key_code); input_number(&key_code);
if (99 == key_code) if (99 == key_code)
@@ -267,7 +274,7 @@ static INT8 decode_as_tv(char *file_name, UINT8 ir_hex_encode)
break; break;
} }
length = ir_decode(key_code, user_data, NULL, 0); length = ir_decode(key_code, user_data, NULL, 0);
printf("\n === Binary decoded : %d\n", length); printf("\n === binary decoded : %d\n", length);
for (index = 0; index < length; index++) for (index = 0; index < length; index++)
{ {
printf("%d, ", user_data[index]); printf("%d, ", user_data[index]);
@@ -281,10 +288,10 @@ static INT8 decode_as_tv(char *file_name, UINT8 ir_hex_encode)
} }
static void print_usage(const char *progn) { static void print_usage(const char *progn) {
printf("Usage: %s [function] [file] [subcate]\n" printf("usage: %s [function] [file] [subcate]\n"
"[function] : 0 - decode for AC; 1 - decode for TV\n" "[function] : 0 - decode for AC; 1 - decode for others\n"
"[file] : the remote control binary file\n" "[file] : the remote control binary file\n"
"[subcate] : the sub_cate value from remote_index", progn); "[sub_cate] : the sub_cate value from remote_index", progn);
} }
int main(int argc, char *argv[]) int main(int argc, char *argv[])
@@ -304,17 +311,17 @@ int main(int argc, char *argv[])
switch (function) switch (function)
{ {
case '0': case '0':
printf("Decode %s as status-typed binary\n", argv[2]); printf("decode %s as status-typed binary\n", argv[2]);
decode_as_ac(argv[2]); decode_as_ac(argv[2]);
break; break;
case '1': case '1':
printf("Decode %s as command-typed binary in sub_cate %d\n", argv[2], ir_hex_encode); printf("decode %s as command-typed binary in sub_cate %d\n", argv[2], ir_hex_encode);
decode_as_tv(argv[2], ir_hex_encode); decode_as_tv(argv[2], ir_hex_encode);
break; break;
default: default:
printf("Decode functionality not supported : %c\n", function); printf("decode functionality not supported : %c\n", function);
break; break;
} }
} }

View File

@@ -4,6 +4,7 @@ import net.irext.decode.sdk.bean.ACStatus;
import net.irext.decode.sdk.bean.TemperatureRange; import net.irext.decode.sdk.bean.TemperatureRange;
import net.irext.decode.sdk.utils.Constants; import net.irext.decode.sdk.utils.Constants;
/** /**
* Filename: IRDecode.java * Filename: IRDecode.java
* Revised: Date: 2017-04-22 * Revised: Date: 2017-04-22
@@ -66,11 +67,15 @@ public class IRDecode {
} }
public int[] decodeBinary(int keyCode, ACStatus acStatus, int changeWindDir) { public int[] decodeBinary(int keyCode, ACStatus acStatus, int changeWindDir) {
int[] decoded; int []decoded;
synchronized (mSync) { synchronized (mSync) {
if (null == acStatus) { if (null == acStatus) {
acStatus = new ACStatus(); acStatus = new ACStatus();
} }
// validate ac status
if (!validateAcStatus(acStatus, keyCode, changeWindDir)) {
return new int[0];
}
decoded = irDecode(keyCode, acStatus, changeWindDir); decoded = irDecode(keyCode, acStatus, changeWindDir);
} }
return decoded; return decoded;
@@ -86,7 +91,7 @@ public class IRDecode {
public int[] getACSupportedMode() { public int[] getACSupportedMode() {
// cool, heat, auto, fan, de-humidification // cool, heat, auto, fan, de-humidification
int[] retSupportedMode = {0, 0, 0, 0, 0}; int []retSupportedMode = {0, 0, 0, 0, 0};
int supportedMode = irACGetSupportedMode(); int supportedMode = irACGetSupportedMode();
for (int i = Constants.ACMode.MODE_COOL.getValue(); i <= for (int i = Constants.ACMode.MODE_COOL.getValue(); i <=
Constants.ACMode.MODE_DEHUMIDITY.getValue(); i++) { Constants.ACMode.MODE_DEHUMIDITY.getValue(); i++) {
@@ -97,7 +102,7 @@ public class IRDecode {
public int[] getACSupportedWindSpeed(int acMode) { public int[] getACSupportedWindSpeed(int acMode) {
// auto, low, medium, high // auto, low, medium, high
int[] retSupportedWindSpeed = {0, 0, 0, 0}; int []retSupportedWindSpeed = {0, 0, 0, 0};
int supportedWindSpeed = irACGetSupportedWindSpeed(acMode); int supportedWindSpeed = irACGetSupportedWindSpeed(acMode);
for (int i = Constants.ACWindSpeed.SPEED_AUTO.getValue(); for (int i = Constants.ACWindSpeed.SPEED_AUTO.getValue();
i <= Constants.ACWindSpeed.SPEED_HIGH.getValue(); i <= Constants.ACWindSpeed.SPEED_HIGH.getValue();
@@ -109,7 +114,7 @@ public class IRDecode {
public int[] getACSupportedSwing(int acMode) { public int[] getACSupportedSwing(int acMode) {
// swing-on, swing-off // swing-on, swing-off
int[] retSupportedSwing = {0, 0}; int []retSupportedSwing= {0, 0};
int supportedSwing = irACGetSupportedSwing(acMode); int supportedSwing = irACGetSupportedSwing(acMode);
for (int i = Constants.ACSwing.SWING_ON.getValue(); for (int i = Constants.ACSwing.SWING_ON.getValue();
i <= Constants.ACSwing.SWING_OFF.getValue(); i <= Constants.ACSwing.SWING_OFF.getValue();
@@ -123,4 +128,31 @@ public class IRDecode {
// how many directions supported by specific AC // how many directions supported by specific AC
return irACGetSupportedWindDirection(acMode); return irACGetSupportedWindDirection(acMode);
} }
private boolean validateAcStatus(ACStatus acStatus, int keyCode, int changeWindDir) {
if (acStatus.getAcPower() != Constants.ACPower.POWER_ON.getValue() &&
acStatus.getAcPower() != Constants.ACPower.POWER_OFF.getValue()) {
return false;
}
if (acStatus.getAcMode() < Constants.ACMode.MODE_COOL.getValue() ||
acStatus.getAcMode() > Constants.ACMode.MODE_DEHUMIDITY.getValue()) {
return false;
}
if (acStatus.getAcTemp() < Constants.ACTemperature.TEMP_16.getValue() ||
acStatus.getAcTemp() > Constants.ACTemperature.TEMP_30.getValue()) {
return false;
}
if (acStatus.getAcWindSpeed() < Constants.ACWindSpeed.SPEED_AUTO.getValue() ||
acStatus.getAcWindSpeed() > Constants.ACWindSpeed.SPEED_HIGH.getValue()) {
return false;
}
if (acStatus.getAcWindDir() < Constants.ACSwing.SWING_ON.getValue() ||
acStatus.getAcWindDir() > Constants.ACSwing.SWING_OFF.getValue()) {
return false;
}
if (changeWindDir != 0 && changeWindDir != 1) {
return false;
}
return true;
}
} }

View File

@@ -46,7 +46,10 @@ public class Constants {
LIGHT(10), LIGHT(10),
BSTB(11), BSTB(11),
CLEANING_ROBOT(12), CLEANING_ROBOT(12),
AIR_CLEANER(13); AIR_CLEANER(13),
DYSON_SERIES(14),
CAMERA(15),
HEATER(16);
private final int id; private final int id;
@@ -168,13 +171,13 @@ public class Constants {
} }
public enum ACFunction { public enum ACFunction {
FUNCTION_SWITCH_POWER(0), FUNCTION_SWITCH_POWER(1),
FUNCTION_CHANGE_MODE(1), FUNCTION_CHANGE_MODE(2),
FUNCTION_TEMPERATURE_UP(2), FUNCTION_TEMPERATURE_UP(3),
FUNCTION_TEMPERATURE_DOWN(3), FUNCTION_TEMPERATURE_DOWN(4),
FUNCTION_SWITCH_WIND_SPEED(9), FUNCTION_SWITCH_WIND_SPEED(5),
FUNCTION_SWITCH_SWING(10), FUNCTION_SWITCH_WIND_DIR(6),
FUNCTION_SWITCH_WIND_DIR(11); FUNCTION_SWITCH_SWING(7);
private final int function; private final int function;