Now, I show you how to use the CAPSENSE technology to unsolder components, and again using the PSoC 62S2 WiFi BT Pioneer Kit board. Below I show you the schematic diagram.
Schematic Diagram
Schematic diagram
How does it work?
- Here I will use the device created in section 3. This gripper-1 will be used to hold a part of the board on which I will desolder a component.
The gripper-1 also helped me to desolder components on a PCB board.
- When I turn on the system the robot arm is positioned according to the initial configuration. That is, servo 1 moves to 30 degrees from the origin.
Between two grippers the PCB board is fixedly clamped as shown in the picture
- When I press the capsense BTN0 button, servo 1 moves to 165 degrees from the origin to hold the PCB with gripper-2. Next, servo 1 moves to 100 degrees from the origin to face gripper 2 to gripper-1. Now I can hold the PCB with both grippers as shown in the attached image.
Its time to desolder a component with the soldering iron
- Since the PCB board is firmly holded, then I can desolder components comfortably. When I finish desoldering I can open the griper-1.
Finally we use the solder extractor to remove the component
- When I press the BTN1 capsense button, servo 1 moves from 100 degrees from the origin to 30 degrees. Here the robot arm releases the PCB board and returns to the position indicated in point 2.
- Additionally, I have configured servo 4 to rotate the gripper with the Capsense sliding bar. This movement can only be done when the robot arm is in the initial position indicated in point 2. When I move my finger to the SLD 0 position, the gripper-2 tilts 90 degrees from the origin.
Prgramming With ModusToolbox
Again as in section 4, I have used the "CAPSENSE_Buttons_and_Slider" example and named the project as Unsoldering_Components_Using_Capsense.
We repeat the same steps already seen to program the other PSoC 62S2 board as a component desoldering iron
Finally, I have modified the "led.c" code. Below I show you the full code.
// AUTHOR: Guillermo Perez Guillen
/*******************************************************************************
* Header files includes
*******************************************************************************/
#include "cybsp.h"
#include "cyhal.h"
#include "led.h"
#include <stdio.h> // added
#include <math.h>
/*******************************************************************************
* Global constants
*******************************************************************************/
#define PWM_LED_FREQ_HZ (1000000lu) /* in Hz */
#define GET_DUTY_CYCLE(x) (100 - x)
/*******************************************************************************
* Global constants
*******************************************************************************/
led_state_t led_state_cur = LED_OFF;
cyhal_pwm_t pwm_led;
cyhal_pwm_t servo_1; // robot arm
cyhal_pwm_t servo_2;
cyhal_pwm_t servo_3;
cyhal_pwm_t servo_4;
cyhal_pwm_t servo_5; // robot gripper-2
/******************************************************************************
* Servo Macros - added
*****************************************************************************/
/* PWM Frequency */
#define PWM_FREQUENCY (50u)
/* PWM Duty-cycle */
#define PWM_DUTY_CYCLE_1 (4.44f) // 30 degrees
#define PWM_DUTY_CYCLE_2 (8.02f) // 100 degrees
#define PWM_DUTY_CYCLE_3 (10.76f) // 150 degrees
#define PWM_DUTY_CYCLE_4 (8.02f) // 100 degrees
#define PWM_DUTY_CYCLE_5 (3.48f) // 10 degrees - robot gripper-2
/*******************************************************************************
* Function Name: update_led_state
********************************************************************************
* Summary:
* This function updates the LED state, based on the touch input.
*
* Parameter:
* ledData: the pointer to the LED data structure
*
*******************************************************************************/
void update_led_state(led_data_t *ledData)
{
if ((led_state_cur == LED_OFF) && (ledData->state == LED_ON))
{
cyhal_pwm_start(&pwm_led);
led_state_cur = LED_ON;
ledData->brightness = LED_MAX_BRIGHTNESS;
for (int i = 65; i <= 90; i++){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
for (int i = 100; i >= 30; i--){ // servo_1 ***
float PWM_DUTY_CYCLE_S1 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_1, PWM_DUTY_CYCLE_S1, PWM_FREQUENCY);
cyhal_pwm_start(&servo_1);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
for (int i = 90; i >= 65; i--){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
for (int i = 8; i <= 60; i++){ // servo_5 *** robot gripper-2 opened
float PWM_DUTY_CYCLE_S5 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_5, PWM_DUTY_CYCLE_S5, PWM_FREQUENCY);
cyhal_pwm_start(&servo_5);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(500);
for (int i = 65; i <= 90; i++){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(250);
for (int i = 60; i >= 10; i--){ // servo_5 *** robot gripper-2 closesd
float PWM_DUTY_CYCLE_S5 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_5, PWM_DUTY_CYCLE_S5, PWM_FREQUENCY);
cyhal_pwm_start(&servo_5);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
}
else if ((led_state_cur == LED_ON) && (ledData->state == LED_OFF))
{
cyhal_pwm_stop(&pwm_led);
led_state_cur = LED_OFF;
ledData->brightness = 0;
for (int i = 30; i <= 165; i++){ // servo_1 ***
float PWM_DUTY_CYCLE_S1 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_1, PWM_DUTY_CYCLE_S1, PWM_FREQUENCY);
cyhal_pwm_start(&servo_1);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(250);
for (int i = 10; i <= 60; i++){ // servo_5 *** robor gripper-2 opened
float PWM_DUTY_CYCLE_S5 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_5, PWM_DUTY_CYCLE_S5, PWM_FREQUENCY);
cyhal_pwm_start(&servo_5);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
for (int i = 90; i >= 65; i--){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(500);
for (int i = 60; i >= 8; i--){ // servo_5 *** robot gripper-2 closed
float PWM_DUTY_CYCLE_S5 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_5, PWM_DUTY_CYCLE_S5, PWM_FREQUENCY);
cyhal_pwm_start(&servo_5);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(250);
for (int i = 65; i <= 90; i++){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
for (int i = 165; i >= 100; i--){ // servo_1 ***
float PWM_DUTY_CYCLE_S1 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_1, PWM_DUTY_CYCLE_S1, PWM_FREQUENCY);
cyhal_pwm_start(&servo_1);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(250);
for (int i = 90; i >= 65; i--){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
cyhal_system_delay_ms(50);
}
else
{
}
if ((LED_ON == led_state_cur) || ((LED_OFF == led_state_cur) && (ledData->brightness > 0)))
{
cyhal_pwm_start(&pwm_led);
uint32_t brightness = (ledData->brightness < LED_MIN_BRIGHTNESS) ? LED_MIN_BRIGHTNESS : ledData->brightness;
uint32_t servo_control_gripper_2 = brightness;
uint32_t PWM_DUTY_CYCLE_GRIPPER_2 = 0.00003 * pow(servo_control_gripper_2, 2) + 0.0472 * servo_control_gripper_2 + 3;
/* Drive the LED with brightness */
cyhal_pwm_set_duty_cycle(&pwm_led, GET_DUTY_CYCLE(brightness), PWM_LED_FREQ_HZ);
cyhal_pwm_set_duty_cycle(&servo_4, PWM_DUTY_CYCLE_GRIPPER_2, PWM_FREQUENCY); // servo 4
cyhal_pwm_start(&servo_4);
led_state_cur = LED_ON;
}
}
/*******************************************************************************
* Function Name: initialize_led
********************************************************************************
* Summary:
* Initializes a PWM resource for driving an LED.
*
*******************************************************************************/
cy_rslt_t initialize_led(void)
{
cy_rslt_t rslt;
rslt = cyhal_pwm_init(&pwm_led, CYBSP_USER_LED, NULL);
rslt = cyhal_pwm_init(&servo_1, P7_5, NULL); // pinout
rslt = cyhal_pwm_init(&servo_2, P7_6, NULL);
rslt = cyhal_pwm_init(&servo_3, P12_3, NULL);
rslt = cyhal_pwm_init(&servo_4, P12_0, NULL);
rslt = cyhal_pwm_init(&servo_5, P12_1, NULL);
cyhal_pwm_set_duty_cycle(&servo_1, PWM_DUTY_CYCLE_1, PWM_FREQUENCY);
cyhal_pwm_start(&servo_1);
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_pwm_set_duty_cycle(&servo_3, PWM_DUTY_CYCLE_3, PWM_FREQUENCY);
cyhal_pwm_start(&servo_3);
cyhal_pwm_set_duty_cycle(&servo_4, PWM_DUTY_CYCLE_4, PWM_FREQUENCY);
cyhal_pwm_start(&servo_4);
cyhal_pwm_set_duty_cycle(&servo_5, PWM_DUTY_CYCLE_5, PWM_FREQUENCY);
cyhal_pwm_start(&servo_5);
if (CY_RSLT_SUCCESS == rslt)
{
rslt = cyhal_pwm_set_duty_cycle(&pwm_led,
GET_DUTY_CYCLE(LED_MAX_BRIGHTNESS),
PWM_LED_FREQ_HZ);
if (CY_RSLT_SUCCESS == rslt)
{
rslt = cyhal_pwm_start(&pwm_led);
}
}
if (CY_RSLT_SUCCESS == rslt)
{
led_state_cur = LED_ON;
}
return rslt;
}
As in the previ
As in the previous section, I have also used Capsense sliding to control the gripper. Again, all other servos are controlled by the formula obtained in section 3, for example, servo 2 is moved from 65° to 90° with:
for (int i = 65; i <= 90; i++){ // servo_2 ***
float PWM_DUTY_CYCLE_S2 = 0.00003 * pow(i, 2) + 0.0472 * i + 3;
cyhal_pwm_set_duty_cycle(&servo_2, PWM_DUTY_CYCLE_S2, PWM_FREQUENCY);
cyhal_pwm_start(&servo_2);
cyhal_system_delay_ms(20);
}
Discussions
Become a Hackaday.io Member
Create an account to leave a comment. Already have an account? Log In.