Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update/ion kit 1.0.0 #6

Merged
merged 18 commits into from
Jan 19, 2024
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
Show all changes
18 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 11 additions & 2 deletions cpp/CMAKELists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,10 @@ include_directories(${SENSING_DEV_DIR}/include)
link_directories(${SENSING_DEV_DIR}/bin)
link_directories(${SENSING_DEV_DIR}/lib)

# tutorial 0
include_directories(${SENSING_DEV_DIR}/include/aravis-0.8)
include_directories(${SENSING_DEV_DIR}/include/glib-2.0)

# tutorial 0
set(T0 src/tutorial0_get_device_info.cpp)
add_executable(tutorial0_get_device_info ${T0})
target_compile_features(tutorial0_get_device_info PUBLIC cxx_std_17)
Expand All @@ -26,11 +27,19 @@ set(T1 src/tutorial1_display.cpp)
add_executable(tutorial1_display ${T1})
target_compile_features(tutorial1_display PUBLIC cxx_std_17)

# target_link_libraries(tutorieal1_display PRIVATE aravis-0.8.lib)
target_link_libraries(tutorial1_display PRIVATE opencv_world455.lib)
target_link_libraries(tutorial1_display PRIVATE ion-core.lib)
target_link_libraries(tutorial1_display PRIVATE halide.lib)

# tutorial 1
set(T2 src/tutorial2_control_camera.cpp)
add_executable(tutorial2_control_camera ${T2})
target_compile_features(tutorial2_control_camera PUBLIC cxx_std_17)

target_link_libraries(tutorial2_control_camera PRIVATE opencv_world455.lib)
target_link_libraries(tutorial2_control_camera PRIVATE ion-core.lib)
target_link_libraries(tutorial2_control_camera PRIVATE halide.lib)

#
# Allow big object
#
Expand Down
78 changes: 21 additions & 57 deletions cpp/src/tutorial1_display.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,6 @@

using namespace ion;

#ifdef _WIN32
#define MODULE_NAME "ion-bb"
#else
#define MODULE_NAME "libion-bb.so"
#endif


#define FEATURE_GAIN_KEY "Gain"
#define FEATURE_EXPOSURE_KEY "ExposureTime"


std::map<std::string, int32_t> num_bit_shift_map{
{"Mono8", 0}, {"Mono10", 6}, {"Mono12", 4}};
std::map<std::string, int32_t> opencv_mat_type{
Expand All @@ -41,45 +30,22 @@ int positive_pow(int base, int expo){
}
}


template<typename T>
int video(int width, int height, std::string pixel_format, int num_device){
// pipeline setup
Builder b;
b.set_target(Halide::get_host_target());
b.with_bb_module(MODULE_NAME);

// set port
Port dispose_p{ "dispose", Halide::type_of<bool>() };
Port gain_p{ "gain", Halide::type_of<double>(), 1 };
Port exposure_p{ "exposure", Halide::type_of<double>(), 1 };
b.set_target(ion::get_host_target());
b.with_bb_module("ion-bb");

Node n = b.add(bb_name[pixel_format])(dispose_p, gain_p, exposure_p)
// add BB to pipeline
Node n = b.add(bb_name[pixel_format])()
.set_param(
Param{"num_devices", std::to_string(num_device)},
Param{"pixel_format_ptr", pixel_format},
Param{"frame_sync", "true"},
Param{"gain_key", FEATURE_GAIN_KEY},
Param{"exposure_key", FEATURE_EXPOSURE_KEY},
Param{"realtime_diaplay_mode", "false"}
Param("num_devices", num_device),
Param("frame_sync", true),
Param("realtime_diaplay_mode", false)
);

double *gains = (double*) malloc (sizeof (double) * num_device);
double *exposures = (double*) malloc (sizeof (double) * num_device);
for (int i = 0; i < num_device; ++i){
gains[i] = 40.0;
exposures[i] = 100.0;
}


Halide::Buffer<double> gain_buf(gains, std::vector< int >{num_device});
Halide::Buffer<double> exposure_buf(exposures, std::vector< int >{num_device});


PortMap pm;
pm.set(gain_p, gain_buf);
pm.set(exposure_p, exposure_buf);

// portmapping from output port to output buffer
std::vector< int > buf_size = std::vector < int >{ width, height };
if (pixel_format == "RGB8"){
buf_size.push_back(3);
Expand All @@ -88,32 +54,31 @@ int video(int width, int height, std::string pixel_format, int num_device){
for (int i = 0; i < num_device; ++i){
output.push_back(Halide::Buffer<T>(buf_size));
}
pm.set(n["output"], output);
n["output"].bind(output);

int loop_num = 1000;
int loop_num = 100;
int coef = positive_pow(2, num_bit_shift_map[pixel_format]);
for (int i = 0; i < loop_num; ++i)
{
pm.set(dispose_p, i == loop_num-1);
// JIT compilation and execution of pipelines with Builder.
try {
b.run(pm);
b.run();
}catch(std::exception& e){

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can delete try-catch from here and delegate to outermost try-catch block.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in a85a0a5

// e.what() shows the error message if pipeline build/run was failed.
std::cerr << "Failed to build pipeline" << std::endl;
std::cerr << e.what() << std::endl;
exit(1);
// e.what() shows the error message if pipeline build/run was failed.
std::cerr << "Failed to build pipeline" << std::endl;
std::cerr << e.what() << std::endl;
exit(1);
}

// Convert the retrieved buffer object to OpenCV buffer format.
for (int i = 0; i < num_device; ++i){
cv::Mat img(height, width, opencv_mat_type[pixel_format]);
std::memcpy(img.ptr(), output[i].data(), output[i].size_in_bytes());
img *= positive_pow(2, num_bit_shift_map[pixel_format]);
img *= coef;
cv::imshow("image" + std::to_string(i), img);
}

// Wait for key input
// When any key is pressed, close the currently displayed image and proceed to the next frame.
// Wait for 1ms
cv::waitKey(1);
}
return 0;
Expand All @@ -122,9 +87,9 @@ int video(int width, int height, std::string pixel_format, int num_device){
int main(int argc, char *argv[])
{
try{
int32_t width = 640;
int32_t height = 480;
int32_t num_device = 2;
int32_t width = 1920;
int32_t height = 1080;
int32_t num_device = 1;
std::string pixelformat = "Mono8";

if (pixelformat == "Mono8"){
Expand All @@ -133,7 +98,6 @@ int main(int argc, char *argv[])
int ret = video<uint16_t>(width, height, pixelformat, num_device);
}


}catch(std::exception& e){

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should catch ion::Error additionally to std::exception.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 87d09cf

std::cerr << e.what() << std::endl;
exit(1);
Expand Down
129 changes: 129 additions & 0 deletions cpp/src/tutorial2_control_camera.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,129 @@
#include <opencv2/core.hpp>
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>

#include <ion/ion.h>

#include <exception>
#include <string>
#include <map>

using namespace ion;

std::map<std::string, int32_t> num_bit_shift_map{
{"Mono8", 0}, {"Mono10", 6}, {"Mono12", 4}};
std::map<std::string, int32_t> opencv_mat_type{
{"Mono8", CV_8UC1}, {"Mono10", CV_16UC1}, {"Mono12", CV_16UC1}};
std::map<std::string, std::string> bb_name{
{"Mono8", "image_io_u3v_cameraN_u8x2"},
{"Mono10", "image_io_u3v_cameraN_u16x2"},
{"Mono12", "image_io_u3v_cameraN_u16x2"}};

int positive_pow(int base, int expo){
if (expo <= 0){
return 1;
}
if (expo == 1){
return base;
}else{
return base * positive_pow(base, expo-1);
}
}

double gain0 = 35.0;
double exposuretime0 = 50.0;
double gain1 = 47.0;
double exposuretime1 = 100.0;

template<typename T>
int video(int width, int height, std::string pixel_format, int num_device){
// pipeline setup
Builder b;
b.set_target(ion::get_host_target());
b.with_bb_module("ion-bb");

// add BB to pipeline
Node n;
if (num_device == 1){
n = b.add(bb_name[pixel_format])(&gain0, &exposuretime0)
.set_param(
Param("num_devices", num_device),
Param("frame_sync", true),
Param("realtime_diaplay_mode", false),
Param("enable_control", true),
Param("gain_key", "Gain"),
Param("exposure_key", "ExposureTime")
);
}else if (num_device == 2){
n = b.add(bb_name[pixel_format])(&gain0, &exposuretime0, &gain1, &exposuretime1)
.set_param(
Param("num_devices", num_device),
Param("frame_sync", true),
Param("realtime_diaplay_mode", false),
Param("enable_control", true),
Param("gain_key", "Gain"),
Param("exposure_key", "ExposureTime")
);
}else{
throw("Set the same number of gains and exposure times as the number of devices.");
}

// portmapping from output port to buffer
std::vector< int > buf_size = std::vector < int >{ width, height };
if (pixel_format == "RGB8"){
buf_size.push_back(3);
}
std::vector<Halide::Buffer<T>> output;
for (int i = 0; i < num_device; ++i){
output.push_back(Halide::Buffer<T>(buf_size));
}
n["output"].bind(output);

int loop_num = 100;
int coef = positive_pow(2, num_bit_shift_map[pixel_format]);
for (int i = 0; i < loop_num; ++i)
{
// JIT compilation and execution of pipelines with Builder.
try {
b.run();
}catch(std::exception& e){
// e.what() shows the error message if pipeline build/run was failed.
std::cerr << "Failed to build pipeline" << std::endl;
std::cerr << e.what() << std::endl;
exit(1);
}

// Convert the retrieved buffer object to OpenCV buffer format.
for (int i = 0; i < num_device; ++i){
cv::Mat img(height, width, opencv_mat_type[pixel_format], output[i].data());
img *= coef;
cv::imshow("image" + std::to_string(i), img);
}

// Wait for 1ms
cv::waitKey(1);
}
return 0;
}

int main(int argc, char *argv[])
{
try{
int32_t width = 1920;
int32_t height = 1080;
int32_t num_device = 1;
std::string pixelformat = "Mono8";

if (pixelformat == "Mono8"){
int ret = video<uint8_t>(width, height, pixelformat, num_device);
}else{
int ret = video<uint16_t>(width, height, pixelformat, num_device);
}


}catch(std::exception& e){
std::cerr << e.what() << std::endl;
exit(1);
}
return 0;
}
47 changes: 10 additions & 37 deletions python/tutorial1_display.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,12 @@

from ionpy import Node, Builder, Buffer, PortMap, Port, Param, Type, TypeCode

if os.name == 'nt':
module_name = 'ion-bb.dll'
elif os.name == 'posix':
module_name = 'libion-bb.so'

if __name__ == "__main__":

# device information
width = 1280
height = 960
pixelformat = "RGB8"
width = 1920
height = 1080
pixelformat = "Mono8"
num_device = 1

# the following items varies by PixelFormat
Expand All @@ -41,36 +36,18 @@
# pipeline setup
builder = Builder()
builder.set_target('host')
builder.with_bb_module(module_name)

# set port
dispose_p = Port('dispose', Type(TypeCode.Uint, 1, 1), 0)
gain_p = Port('gain', Type(TypeCode.Float, 64, 1), 1)
exposuretime_p = Port('exposuretime', Type(TypeCode.Float, 64, 1), 1)
builder.with_bb_module('ion-bb')

# set params
num_devices = Param('num_devices', str(num_device))
pixel_format_ptr = Param('pixel_format_ptr', pixelformat)
frame_sync = Param('frame_sync', 'false')
gain_key = Param('gain_key', 'Gain')
exposure_key = Param('exposure_key', 'ExposureTime')
realtime_diaplay_mode = Param('realtime_diaplay_mode', 'true')

# add a node to pipeline
node = builder.add(bb_name)\
.set_port([dispose_p, gain_p, exposuretime_p, ])\
.set_param([num_devices, pixel_format_ptr, frame_sync, gain_key, exposure_key, realtime_diaplay_mode, ])
.set_param([num_devices, frame_sync, realtime_diaplay_mode, ])
output_p = node.get_port('output')

# create halide buffer for input port
gain_data = np.array([48.0])
exposure_data = np.array([100.0])

gains = Buffer(Type(TypeCode.Float, 64, 1), (1,))
exposures = Buffer(Type(TypeCode.Float, 64, 1), (1,))
gains.write(gain_data.tobytes(order='C'))
exposures.write(exposure_data.tobytes(order='C'))

# create halide buffer for output port
outputs = []
output_size = (width, height, )
Expand All @@ -79,10 +56,7 @@
outputs.append(Buffer(Type(TypeCode.Uint, depth_of_buffer, 1), output_size))

# set I/O ports
port_map = PortMap()
port_map.set_buffer(gain_p, gains)
port_map.set_buffer(exposuretime_p, exposures)
port_map.set_buffer_array(output_p, outputs)
output_p[0].bind(outputs[0])
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

after pull fixstars/ion-kit#207
you can use output_p.bind(outputs)


# prepare Opencv
buf_size_opencv = (height, width)
Expand All @@ -92,18 +66,17 @@
output_byte_size *= 3

loop_num = 100
coef = pow(2, num_bit_shift)

for x in range(loop_num):
port_map.set_u1(dispose_p, x==loop_num-1)

# running the builder
builder.run(port_map)
builder.run()
output_bytes = outputs[0].read(output_byte_size)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

read is no longer needed. You can create ion.Buffer passing numpy array (Buffer(array=numpy_array)) and you can access data through numpy array without ion.Buffer.read/write operation

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 24b9ed0


output_np_HxW = np.frombuffer(output_bytes, data_type).reshape(buf_size_opencv)
output_np_HxW *= pow(2, num_bit_shift)
output_np_HxW *= coef

cv2.imshow("A", output_np_HxW)
cv2.imshow("img", output_np_HxW)
cv2.waitKey(1)

cv2.destroyAllWindows()
Expand Down
Loading