Mục lục:

Biến Roomba của bạn thành Mars Rover: 5 bước
Biến Roomba của bạn thành Mars Rover: 5 bước

Video: Biến Roomba của bạn thành Mars Rover: 5 bước

Video: Biến Roomba của bạn thành Mars Rover: 5 bước
Video: Tàu Du Hành Perseverance Mars Rover Hạ Cánh- Câu Chuyện Ẩn Sau Nó 2024, Tháng mười một
Anonim
Biến Roomba của bạn thành Mars Rover
Biến Roomba của bạn thành Mars Rover

Bước 1: Thu thập tài liệu của bạn

Để hoàn thành dự án này, bạn sẽ cần thu thập các tài liệu sau:

1 Robot Roomba

1 Bộ Raspberry Pi

1 máy quay video

Truy cập vào MATLAB

Bước 2: Tải xuống Hộp công cụ Roomba cho MATLAB

Tải xuống Hộp công cụ Roomba cho MATLAB
Tải xuống Hộp công cụ Roomba cho MATLAB
Tải xuống Hộp công cụ Roomba cho MATLAB
Tải xuống Hộp công cụ Roomba cho MATLAB

Chạy đoạn mã sau để cài đặt các hộp công cụ cần thiết để hoàn thành dự án này.

chức năng roombaInstall

clc;

% danh sách các tệp cần cài đặt

files = {'roomba.m', 'roombaSim.m', 'roombaSimGUI.m', 'roombaSimGUI.fig'};

% vị trí để cài đặt từ

options = weboptions ('Tên tập tin chứng chỉ', ''); % yêu cầu nó bỏ qua các yêu cầu chứng chỉ

server = 'https://ef.engr.utk.edu/ef230/projects/roomba-f2016/install/';

dlgTitle = 'Cài đặt / Cập nhật Roomba';

% hiển thị mục đích và nhận xác nhận

nhắc = {

'Chương trình này sẽ tải xuống các tệp Roomba EF 230 này:'

''

strjoin (tệp, '')

''

'vào thư mục này:'

''

đĩa CD

''

'Bạn có muốn tiếp tục? '

};

tiếng kêu bíp;

yn = questdlg (lời nhắc,…

dlgTitle,…

'Có', 'Không', 'Có');

if ~ strcmp (yn, 'Yes'), return; kết thúc

% lấy danh sách các tệp tồn tại

current_files = files (cellfun (@exist, files)> 0);

if ~ isempty (các tập tin hiện có)

Hãy chắc chắn rằng nó thực sự ổn để thay thế chúng

prompt = {'Bạn đang thay thế (các) tệp này:'

''

strjoin (hiện_files, '')

''

'OK để thay thế?'

};

tiếng kêu bíp;

yn = questdlg (lời nhắc,…

dlgTitle,…

'Có', 'Không', 'Có');

if ~ strcmp (yn, 'Yes'), return; kết thúc

kết thúc

% tải xuống các tệp

cnt = 0;

cho i = 1: length (tệp)

f = tệp {i};

disp (['Đang tải xuống' f]);

cố gắng

url = [máy chủ f];

websave (f, url, tùy chọn); % đã thêm tùy chọn để tránh lỗi bảo mật

cnt = cnt + 1;

chụp lấy

disp (['Lỗi khi tải xuống' f]);

dummy = [f '.html'];

nếu tồn tại (dummy, 'file') == 2

xóa (giả)

kết thúc

kết thúc

kết thúc

nếu cnt == độ dài (tệp)

msg = 'Cài đặt thành công';

waitfor (msgbox (msg, dlgTitle));

khác

msg = 'Lỗi Cài đặt - xem cửa sổ lệnh để biết chi tiết';

waitfor (errordlg (msg, dlgTitle));

kết thúc

end% roombaInstall

Bước 3: Kết nối với Roomba của bạn

Bây giờ đã đến lúc kết nối với Roomba của bạn bằng WiFi. Sử dụng 2 ngón tay, nhấn đồng thời nút Dock và Spot để bật hoặc đặt lại Roomba của bạn. Tiếp theo, Chạy mã r = roomba (# của Roomba của bạn) trong cửa sổ lệnh của MATLAB để kết nối với rô bốt của bạn. Khi bạn đã thực hiện lệnh này, Roomba của bạn sẽ sẵn sàng hoạt động.

Bước 4: Chọn cách bạn muốn kiểm soát Roomba của mình

Chọn cách bạn muốn kiểm soát Roomba của mình
Chọn cách bạn muốn kiểm soát Roomba của mình
Chọn cách bạn muốn kiểm soát Roomba của mình
Chọn cách bạn muốn kiểm soát Roomba của mình

Có hai cách để bạn có thể điều khiển Roomba của mình: tự động hoặc sử dụng điện thoại thông minh làm bộ điều khiển.

Nếu bạn chọn tự lái Roomba, bạn sẽ cần sử dụng ba cảm biến tích hợp: cảm biến vách đá, cảm biến va chạm và cảm biến ánh sáng.

Để sử dụng điện thoại thông minh, trước tiên bạn cần kết nối điện thoại thông minh với máy tính bằng cách làm theo các bước dưới đây.

LƯU Ý: Máy tính và điện thoại thông minh của bạn cần phải kết nối với cùng một mạng WiFi để kết nối đúng cách!

1. Tải xuống ứng dụng MATLAB từ cửa hàng ứng dụng trên thiết bị của bạn.

2. Nhập "connector on" vào cửa sổ lệnh của bạn và đặt mật khẩu cần được nhập vào cả hai thiết bị.

3. Sau khi làm như vậy, MATLAB sẽ cung cấp cho bạn địa chỉ IP máy tính của bạn. Bạn cần truy cập trang cài đặt trong ứng dụng MATLAB trên điện thoại thông minh của mình và thêm máy tính bằng địa chỉ IP đã cho và mật khẩu bạn đã nhập trước đó.

4. Trong cửa sổ lệnh trên máy tính của bạn, hãy nhập mã m = mobiledev và mã này sẽ khởi tạo điện thoại thông minh của bạn làm bộ điều khiển cho Roomba của bạn.

5. Máy tính và điện thoại thông minh của bạn đã sẵn sàng để sử dụng ngay bây giờ.

Bước 5: Lái Roomba của bạn

Bây giờ bạn đã có tất cả các công cụ cần thiết để tạo Mars Rover của mình, bạn đã sẵn sàng tạo mã của riêng mình. Chúng tôi đã đính kèm một mã ví dụ bên dưới cho cả lái xe tự động và lái xe điều khiển bằng điện thoại thông minh.

Lái xe tự hành

function Explore_modified (r)

% đối số đầu vào: 1 đối tượng roomba, r

% đối số đầu ra: không có

%sự mô tả:

Hàm% sử dụng vòng lặp while vô hạn để cho phép tự trị

% khám phá môi trường xung quanh của bot.

%

% funciton cũng cung cấp hướng dẫn cho roomba về những việc cần làm trong

% các tình huống sau: (Các) bánh xe mất (các) tiếp xúc với mặt đất, an

Đối tượng% được phát hiện ở phía trước hoặc ở hai bên của bot và

% giảm đột ngột được phát hiện ở phía trước hoặc ở hai bên của bot.

%

% hướng dẫn điển hình bao gồm các lệnh di chuyển nhằm tối đa hóa

% thăm dò hoặc tránh một mối nguy hiểm được phát hiện và các lệnh để giao tiếp

% thông tin liên quan đến khám phá của bot (hình ảnh), vị trí (biểu đồ), % và trạng thái (cảnh báo bị mắc kẹt) với người dùng qua matlab và / hoặc email. Vài

% lệnh âm thanh được thêm vào để thưởng thức.

% khả năng thiết lập email

mail = '[email protected]';

mật khẩu = 'EF230Roomba';

setpref ('Internet', 'SMTP_Server', 'smtp.gmail.com');

setpref ('Internet', 'E_mail', thư);

setpref ('Internet', 'SMTP_Username', mail);

setpref ('Internet', 'SMTP_Password', mật khẩu);

props = java.lang. System.getProperties;

props.setProperty ('mail.smtp.starttls.enable', 'true');

props.setProperty ('mail.smtp.auth', 'true');

props.setProperty ('mail.smtp.socketFactory.class', 'javax.net.ssl. SSLSocketFactory');

props.setProperty ('mail.smtp.socketFactory.port', '465');

% r = roomba (19)

r.beep ('G2 ^^, G2 ^^, G2 ^^, G2 ^^, A2 ^^, A2 ^^, G1 ^^, E1 ^^, C2 ^^, C2 ^^, C1 ^^, C1 ^^, D1 ^^, C1 ^^, D2 ^^, E4 ^^, G2 ^^, G2 ^^, G2 ^^, G2 ^^, A2 ^^, A2 ^^, G1 ^^, E1 ^^, C2 ^^, C2 ^^, C2 ^^, E1 ^^, E1 ^^, E1 ^^, D1 ^^, C4 ^^ ');

v =.1;

phản_mạng = 2700; % đặt giá trị tham chiếu của cảm biến vách đá

lightBumper_datum = 200; % set light Giá trị tham chiếu của cảm biến đệm

pos = [0, 0]; % biến để lưu trữ vị trí với số liệu được khởi tạo

góc = 0; % đặt góc tham chiếu

netangle = 0; % độ dịch chuyển góc thực

i = 2; % vòng lặp để thêm hàng vào biến lưu trữ vị trí

dist = 0;

r.setDriveVelocity (v, v); % bắt đầu roomba về phía trước

trong khi đúng

Cliff = r.getCliffSensors;

Bump = r.getBumpers;

Light = r.getLightBumpers;

RandAngle = randi ([20, 60], 1); % tạo ra 1 góc ngẫu nhiên từ 20 đến 60 độ. Được sử dụng để ngăn không cho bot bị mắc kẹt trong vòng lặp

% Phải làm gì nếu một hoặc nhiều bánh xe mất tiếp xúc với mặt đất:

% dừng chuyển động, gửi một email cảnh báo với hình ảnh xung quanh, % và hỏi người dùng có nên tiếp tục hay chờ trợ giúp

nếu Bump.rightWheelDrop == 1 || Bump.leftWheelDrop == 1

r.stop

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

r.beep ('F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^, F # 1 ^^, C1 ^^ ')

img = r.getImage;

imwrite (img, 'kẹt.png');

%--------------------------

imfile = 'kẹt.png';

vị trí = savepos (pos);

%---------------------------

sendmail (mail, 'HELP!', 'Tôi đang mắc kẹt trên vách đá!', {imfile, position})

list = {'Tiếp tục', 'Dừng lại'};

idx = menu ('Tôi nên làm gì?', list);

nếu idx == 2

nghỉ

kết thúc

% Phải làm gì nếu một đối tượng được phát hiện trước bot:

% dừng lại, quay lại, chụp ảnh, thông báo cho người dùng về việc khám phá

% qua email, quay 90 độ và tiếp tục khám phá

elseif Light.leftCenter> lightBumper_datum || Light.rightCenter> lightBumper_datum || Bump.front == 1

r.stop;

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

r.moveDistance (-. 125);

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

r.beep ('A1 ^, A1 ^, A4 ^, A2 ^, G2 ^, G2 ^, G4 ^, Bb2 ^, Bb2 ^, Bb3.5 ^, G1 ^, A8 ^')

img = r.getImage;

imwrite (img, 'FrontBump.png')

%--------------------------

imfile = 'FrontBump.png';

vị trí = savepos (pos);

%---------------------------

sendmail (mail, "Alert!", "I found something!", {imfile, position})

góc = 90;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.setDriveVelocity (v, v);

% Phải làm gì nếu đối tượng được phát hiện ở bên trái của bot:

% dừng lại, quay về phía đối tượng, sao lưu, chụp ảnh, cảnh báo

% người dùng khám phá qua email, quay 90 độ và tiếp tục khám phá

elseif Light.leftFront> lightBumper_datum || Light.left> lightBumper_datum || Bump.left == 1

r.stop;

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

góc = 30;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.moveDistance (-. 125);

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

r.beep ('A4 ^, A4 ^, G1 ^, E1 ^, C3.5 ^, C2 ^^, C1 ^, C1 ^, C2 ^, D2 ^, D2 ^, E8 ^')

img = r.getImage;

imwrite (img, 'LeftBump.png')

%--------------------------

imfile = 'LeftBump.png';

vị trí = savepos (pos);

%---------------------------

sendmail (mail, "Alert!", "I found something!", {imfile, position})

góc = -90;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.setDriveVelocity (v, v);

% Phải làm gì nếu đối tượng được phát hiện ở bên phải của bot:

% dừng lại, quay về phía đối tượng, sao lưu, chụp ảnh, cảnh báo

% người dùng khám phá qua email, quay 90 độ và tiếp tục khám phá

elseif Light.rightFront> lightBumper_datum || Light.right> lightBumper_datum || Bump.right == 1

r.stop;

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

góc = -30;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.moveDistance (-. 125);

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

tạm dừng (1.5);

r.beep ('C1 ^, C1 ^, C2 ^, D2 ^, D2 ^, C8 ^')

img = r.getImage;

imwrite (img, 'RightBump.png')

%--------------------------

imfile = 'RightBump.png';

vị trí = savepos (pos);

%---------------------------

sendmail (mail, 'Alert!', 'I found something!', {imfile, position});

góc = 90;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.setDriveVelocity (v, v);

% Phải làm gì nếu phát hiện thấy vách đá ở bên trái bot:

% dừng lại, lùi lại phía sau, rẽ phải, tiếp tục khám phá

elseif Cliff.left <Reflect_datum || Cliff.leftFront <Reflect_datum

r.stop;

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

r.moveDistance (-. 125);

dist = r.getDistance;

pos (i, 1) = pos (i-1, 1) + dist * sind (netangle); % lấy x tọa độ

pos (i, 2) = pos (i-1, 2) + dist * cosd (netangle); % lấy tọa độ y

i = i + 1;

góc = -RandAngle;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.setDriveVelocity (v, v);

% Phải làm gì nếu phát hiện thấy vách đá ở bên phải bot:

% dừng lại, lùi về phía sau, rẽ trái, tiếp tục khám phá

elseif Cliff.right <Ref_datum || Cliff.rightFront <Reflect_datum

r.stop;

dist = r.getDistance;

pos (i, 1) = dist * sind (angle); % lấy x tọa độ

pos (i, 2) = dist * cosd (angle); % lấy tọa độ y

i = i + 1;

r.moveDistance (-. 125);

góc = RandAngle;

netangle = hình tam giác + góc;

r.turnAngle (góc);

r.setDriveVelocity (v, v);

kết thúc

kết thúc

Bộ điều khiển điện thoại thông minh

Options = {'Autonomous', 'Manual Control'}

Prompt = menu ('Bạn muốn điều khiển rover như thế nào?', Tùy chọn)

m = mobiledev

r = roomba (19)

nếu Nhắc == 1

Nhà thám hiểm)

khác

trong khi đúng

tạm dừng (.5)

PhoneData = m. Orientation;

Azi = PhoneData (1);

Pitch = PhoneData (2);

Bên = Dữ liệu Điện thoại (3);

nếu Bên> 130 || Cạnh <-130% nếu điện thoại được lật úp xuống, dừng vòng lặp roomba và thoát

r.stop

r.beep ('C, C, C, C')

nghỉ

elseif Side> 25 && Side <40% nếu xoay điện thoại sang một bên từ 25 đến 40 độ, quay sang trái 5 độ

r.turnAngle (-5);

elseif Side> 40% nếu xoay điện thoại sang một bên trên 40 độ, quay sang trái 45 độ

r.turnAngle (-45)

elseif Side-40% nếu xoay điện thoại sang một bên trong khoảng -25 đến -40 độ, rẽ phải 5 độ

r.turnAngle (5);

elseif Bên <-40% nếu xoay điện thoại sang một bên dưới -40 độ, quay sang trái 45 độ

r.turnAngle (45)

kết thúc

% Nếu điện thoại được giữ gần tiêu đề, hãy chụp ảnh và vẽ biểu đồ

nếu Pitch <-60 && hình ảnh <= 9

r.beep

img = r.getImage;

subplot (3, 3, hình ảnh)

imshow (img)

kết thúc

% di chuyển về phía trước và phía sau dựa trên hướng trước và sau

nếu Cao độ> 15 && Cao độ <35% nếu cao độ từ 15 đến 35 độ di chuyển về phía trước trong khoảng cách ngắn

% nhận dữ liệu cản sáng trước khi di chuyển

litBump = r.getLightBumpers;

nếu litBump.leftFront> 500 || litBump.leftCenter> 500 || litBump.rightCenter> 500 || litBump.rightFront> 500% nếu có thứ gì đó ở phía trước roomba và sẽ nhấn nếu nó di chuyển về phía trước tạo ra tiếng ồn và hiển thị thông báo

r.beep ('C ^^, F # ^, C ^^, F # ^')

khác% di chuyển

r.moveDistance (.03);

% Nhận dữ liệu đệm sau khi di chuyển

Bump = r.getBumpers;

nếu Bump.right == 1 || Bump.left == 1 || Bump.front == 1

r.beep ('A, C, E')

r.moveDistance (-. 01)

kết thúc

% nhận dữ liệu cảm biến vách đá

Cliff = r.getCliffSensors;

nếu Cliff.left> 1500 || Cliff.leftFront> 1500 || Cliff.rightFront> 1500 || Cliff.right> 1500% nếu thứ gì đó kích hoạt cảm biến vách đá coi nó như dung nham và sao lưu

r.beep ('C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C')

r.moveDistance (-. 031)

kết thúc

kết thúc

elseif Cao độ> 35% nếu cao độ lớn hơn 35 độ di chuyển về phía trước khoảng cách xa hơn

% nhận dữ liệu cản sáng trước khi di chuyển

litBump = r.getLightBumpers;

nếu litBump.leftFront> 15 || litBump.leftCenter> 15 || litBump.rightCenter> 15 || litBump.rightFront> 15% nếu thứ gì đó ở phía trước roomba và sẽ nhấn nếu nó di chuyển về phía trước tạo ra tiếng ồn và hiển thị thông báo

r.beep ('C ^^, F # ^, C ^^, F # ^')

khác% di chuyển

r.moveDistance (.3)

% Nhận dữ liệu đệm sau khi di chuyển

Bump = r.getBumpers;

nếu Bump.right == 1 || Bump.left == 1 || Bump.front == 1% nếu bạn gặp thứ gì đó gây ra tiếng ồn, hiển thị thông báo và sao lưu

r.beep ('A, C, E')

r.moveDistance (-. 01)

kết thúc

% nhận dữ liệu cảm biến vách đá sau khi di chuyển

Cliff = r.getCliffSensors;

nếu Cliff.left> 1500 || Cliff.leftFront> 1500 || Cliff.rightFront> 1500 || Cliff.right> 1500% nếu thứ gì đó kích hoạt cảm biến vách đá coi nó như dung nham và sao lưu

r.beep ('C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C')

r.moveDistance (-. 31)

kết thúc

kết thúc

elseif Cao độ-35% nếu cao độ từ -15 đến -35 độ di chuyển lùi lại khoảng cách ngắn

r.moveDistance (-. 03);

% nhận dữ liệu cảm biến vách đá sau khi di chuyển

Cliff = r.getCliffSensors;

nếu Cliff.left> 1500 || Cliff.leftFront> 1500 || Cliff.rightFront> 1500 || Cliff.right> 1500% nếu thứ gì đó kích hoạt cảm biến vách đá coi nó như dung nham và sao lưu

r.beep ('C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C')

r.moveDistance (.04)

kết thúc

elseif Cao độ-60% nếu cao độ từ -35 đến -60 độ di chuyển lùi lại khoảng cách xa hơn

r.moveDistance (-. 3)

% nhận dữ liệu cảm biến vách đá sau khi di chuyển

Cliff = r.getCliffSensors;

nếu Cliff.left> 1500 || Cliff.leftFront> 1500 || Cliff.rightFront> 1500 || Cliff.right> 1500% nếu thứ gì đó kích hoạt cảm biến vách đá coi nó như dung nham và sao lưu

r.beep ('C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C, C ^^, C')

r.moveDistance (.31)

kết thúc

kết thúc

kết thúc

kết thúc

Đề xuất: