Shashank Harshavat sh272                                                                            Norbert Huber nh48

476: Swing

A self-swinging, servo-based scale-model of a playground swing.

Figure 1: The swing.

 

Introduction  |  High Level Design  |  Program/Hardware Design  |  Results  |  Conclusions  |  Appendix

 

Introduction

One day Bruce had an idea. The idea was to build a swing for the 476 Final Project. We took that idea, ran with it, and ended up with this project. The project is based on an Atmel Mega32 MCU. The device consists of a platform mounted in a swing-like fashion. The platform has an attached servo motor that swings a heavy arm. The timing of the arm swing is determined by an accelerometer configured as a tilt sensor. The operation is autonomous. A picture is above in Figure 1. The rest is history.

back to top

 

High Level Design

Rationale

476 Projects are about building cool things that do stuff. Bruce’s idea of the swing was perfect: a simple construction that does something impressive and something that has not been done in lab before. The idea combines microcontroller code with electrical and mechanical components so it is consistent with the spirit of Cornell CDE courses. 

 

Background Math/Physics

The physics and math behind a playground swing are rather simple. We are all familiar with the law of conservation of energy in equation below:

constant

Energy, E, in a closed system is conserved. In an ideal swing, energy is simple converted back and forth from purely potential energy, U, at the ends of the swing, to purely kinetic energy, K, at the bottom of the swing. In our system, we lose some energy to friction, but to make the swing go higher, we are simply adding the potential energy, U, to the swing at appropriate times by raising the center of mass, CM, of our swing. By adding potential energy we are increasing the amount of energy in the swing and therefore make the swing go higher. We can continue to add energy to the swing my lowering the center of mass at the bottom of the swing, where there is no potential energy in the swing to lose.

To initiate the motion, we must force oscillations. The swing can be modeled as a pendulum whose period is given by the equation below:

The period of the swing (assuming small oscillations such as the ones immediately after we initiate the swinging motion), T, is a function of gravity and the length of the swing. We use this equation to force oscillations at the expected frequency in order to get the swing moving.

Reference (and pretty anime): http://www.bsharp.org/physics/stuff/swings.html

 

Logical structure

The main structure of our design is a feedback control system, as shown in Figure 2:

Figure 2: Feedback Control System

 

Our control algorithm is a simple proportional controller. We know when we want the servo to move as a function of the position of the swing. When the swing reaches the appropriate position, as senses by the accelerometer, our control algorithm tells the servo to move, which influences the position of the swing, and the feedback loop continues.

The main structure of our electronics is shown below, in Figure 3:

Figure 3: Electronics Block Diagram

                                                           

Hardware/Software Trade-offs

The most obvious hardware tradeoffs are cost: our limited cost prevents us from using high-quality, perhaps even custom hinges and other components, so there is trade-off in overall performance and aesthetics in favor of staying within the budget.

The second trade-off is using a servo instead of a solenoid. It turns out that affordable, off-the-shelf solenoids cannot generate enough force to sufficiently alter the center of mass of the swing. As such, we decided to use a servo instead.

The third trade-off is using rigid rods instead of more authentic looking chains for the rods that the electronics sit on. We sacrifice authenticity in favor of a better functioning swing. Had we used chains, the lack of stiffness would have introduced random motion to the swing that would have ultimately removed energy from the swing and decreased our oscillations.

The fourth trade-off is relying on software instead of hardware for much of the control system. We elected to do all the programming and data reading in software instead of relying on hardware amplifiers and comparators. This decision reduced the amount of hardware that had to be built and enables us the convenience of making rapid changes in software.

 

Relationship to Known Standards (IEEE, ISO, ANSI, DIN, et. al.)

We did not encounter any situations where we needed conform to standards. The nature of our design is independent of standards such as the IEEE standards that govern RF (radio frequency) communication or ISO/ANSI standards that govern video display conventions.

 

Relevant Patents, Copyrights, and Trademarks

The simplicity of the project, that is, the goal to build something cool that does stuff built from mostly scrap hardware isn’t exactly economically or professionally viable. Our swing swings. That’s it. It is cool that we were able to create an MCU-based swing for virtually no money, but our project remains irrelevant in the world of patents, ™’s, and ©’s.

back to top

 

Program/Hardware Design

The 3 elements to the detailed design: mechanical design, electrical design, and software design.

 

Mechanical Design

The swing is constructed using two metal beams mounted onto a large wooden base. Across the beam is a metal rod which threads through eyehole screws hot glued to two hollow aluminum rods hanging down in parallel. We chose hollow aluminum rods to keep the swing as light as possible in comparison to the oscillating weight. A five-inch by two and half inch Plexiglas plate is attached to the end of the aluminum rods and the electronic hardware is mounted onto it. The Plexiglas is chosen for its non-conductivity. For the weight that is raised and lowered by the servomotor we attached a small cylindrical block of tungsten to a Plexiglas arm, which is also attached to the rotating end of the servomotor. Tungsten is very dense and provides a very compact weight, while the arm is kept long relative to weight to increase the change in potential energy during the operation of the swing. A picture is shown below in Figure 4:

 

Figure 4: The mechanical design.

 

Electrical Design

The electronic hardware in the swing design consists of three major components. First is the Mega32 microcontroller mounted onto the custom PC board, which is responsible for control signals and proper timing. Second is the FreeScale MMA1260 Z-axis, 1.5g Acceleration Sensor that acts as a tilt sensor to monitor the position of the swing. The sensor provides around 4V when completely level to the ground and then decreases its output as it is tilted. Finally there is the S03N GWS servomotor, which lifts and lowers a weight up to 60 degrees in either direction to provide energy to the swing. To control the direction of the motor, the control line needs a 20ms period control signal with varying pulse widths for each position of the motor. The servomotor is used due to its adequate torque and its smooth transition. The acceleration sensor is attached to the custom board and its output is connected to the A0 pin of the MCU so the onboard ADC on the Mega32 can sample the sensor signal. The connecting wire is kept short to minimize electrical noise that may corrupt the signal. The B0 pin of the microcontroller provides the control signal for the servomotor but to ensure that sudden discharges from the servo do not damage the Mega32, the pin is buffered from the servo control line with a 4N35 optoisolator. Also, two DC supplies of 12V and 5V are used to power the MCU and servo respectively to ensure isolation. The sensor is powered at 5V by tapping the converted voltage off of the custom board’s power regulator.  The wiring of the accelerometer is trivial. The schematic of the optoisolator circuit is shown below in Figure 5. An image of the PCB and accelerometer is shown in Figure 6.

 

 

 Figure 5: The optoisolator schematic.

 

Figure 6: The PCB.

 

Software Design

The electronic hardware in the swing design consists of three major components. First is the Mega32 microcontroller mounted onto the custom PC board, which is responsible for control signals and proper timing. Second is the FreeScale MMA1260 Z-axis, 1.5g Acceleration Sensor that acts as a tilt sensor to monitor the position of the swing. The sensor provides around 4V when completely level to the ground and then decreases its output as it is tilted. Finally there is the S03N GWS servomotor, which lifts and lowers a weight up to 60 degrees in either direction to provide energy to the swing. To control the direction of the motor, the control line needs a 20ms period control signal with varying pulse widths for each position of the motor. The servomotor is used due to its adequate torque and its smooth transition. The acceleration sensor is attached to the custom board and its output is connected to the A0 pin of the MCU so the onboard ADC on the Mega32 can sample the sensor signal. The connecting wire is kept short to minimize electrical noise that may corrupt the signal. The B0 pin of the microcontroller provides the control signal for the servomotor but to ensure that sudden discharges from the servo do not damage the Mega32, the pin is buffered from the servo control line with a 4N35 optoisolator. Also, two DC supplies of 12V and 5V are used to power the MCU and servo respectively to ensure isolation. The sensor is powered at 5V by tapping the converted voltage off of the custom board’s power regulator. 

 

All timing in the software is controlled by the timer0 compare interrupt. The clock is prescaled by 64 and the OCR0 is set the to 67. The choice of OCR0 was the result of trial and error starting with 250, then 125, and finally 67. The operation of the swing is divided into three stages. Because the sensor is very inaccurate at low-level amplitudes, we programmed two initial stages that can boost the swing up to amplitude more appropriate for sensor operation. The initial stage is split into two 12-second stages because the swing exhibits different fundamental resonance frequencies at low and medium amplitudes. A long int called initcount is used to count out the 24-second cycle. The interrupt updates initcount while still in the first two stages of operation and uses if else branches to control desired operation. In automatic mode the interrupt toggles a flag variable wait at half the resonance period. When wait is toggled back to zero, if else branches update the char variable width with one of two values. These values correspond to the number of cycles needed to produce .85ms pulses and 2.1ms pulses, which are the correct widths for the extreme positions of the motor. The char variable flip is also toggled every time the width is updated so the interrupt knows to alternate widths. Once the width is set, the interrupt uses the pulsecount variable to time the appropriate sized pulse and output it to B0. The B0 pin is initially high, is set to zero when pulsecount equals the width, and resets to one once pulsecount has counted out 20ms. In the sensor mode the wait flag is set for a much smaller period of time and is not set high again until the width variable is changed. This prevents noise from the sensor readings causing the width to be updated sooner than desired and prevents the motor from triggering rapidly in a small periods of time. Also in sensor mode, the width is updated according to an algorithm rather than automatically after a period of time. The read() function, which is timed by the interrupt and the variable time1 and is called by the main function, reads the ADC samples every 100 cycles. It stores ADCH into Ain0 and then sets ADSCR.6 high to start another conversion. The function also stores the previous 7 samples in Ain1-7. All these 8-bit samples are cast to int’s and summed together. Then the sum is right shifted by three to divide by 8 and find the average of the samples to be stored as the variable tilt. This process acts as a moving average filter in an attempt to filter out random noise that can corrupt the sensor signal.  The read() function also stores the previous two tilt values for use in the triggering algorithm in the interrupt. While in sensor mode the interrupt checks to see if tilt is below a certain threshold which indicates swing is in the center position of its range.  If this is true and if tilt has either stayed the same for the previous two cycles or has increased over time, we know that the swing is in one of the extreme positions of its range or is falling. Then width is updated to the opposite value and the motor swings the weight 120 degrees to the opposite extreme. 

 

Problematic Design Elements

The solenoid approach did not generate enough change in the center of mass to generate the swinging motion.

The accelerometer does not have enough resolution to work at low amplitudes.

back to top

 

Results

Movie of Swing

Speed of Execution

In the end the swing worked better than we had hoped. The autopilot stages worked extremely well in getting the swing to moderate amplitudes and once the sensor mode kicked in the swing really started to fly. We had to turn off the swing just for fear that the swing might swing completely around and break some wiring.

 

 

Accuracy

The sensor works well at larger amplitudes but is completely unreliable at lower amplitudes. If a more sensitive sensor was utilized we could imagine not having to use the autopilot stages at all. The simple moving average filter we utilized to de-noise the sensor signals turned out to work pretty well. We found no need to incorporate a more sophisticated filter, as this would have just eat up computation time.

 

Our initial approach for the swing utilized a solenoid to raise and lower the entire circuit. The problem with this approach was the solenoids were very weak and didn’t move the weight very far so our change in potential energy was very small. Also the solenoids motion was very jerky and this caused sudden vibration on the swing that both disrupted the sensor and also disrupted the swinging motion. Bruce and another one of the swing groups suggested we switch to a servo. By changing to the servo, we were able to lift much more weight for larger range of motion with very smooth transition. Regretfully we did burn out one servo due to overloading. Other than that the servo turned out ideal.

 

Design Safety

As far as safety, we always made sure for high amplitudes to never stand in the path of the swing or point the swing at any other groups. We made sure everything that could potentially fly off was firmly attached to the swing. Repetitive noise from the servo may have annoyed some of the groups working next to us so we apologize. Still in the end, I think the fully functional swing gave the other groups something interesting to look at while they were taking a break from their own work. No one was hurt in the process of making this swing.

 

Interference (e.g. CPU noise, RF noise)

We had no relevant interference issues with other groups.

 

Usability

The simplicity of our design allows anybody to simply walk up to the swing, flip the switches, and stand back to watch it go. Although the design required the information obtained throughout educational experience, the final product is as simple as a child’s toy.

back to top

 

Conclusions

Result Analysis

Our swing works a lot better than expected. Our initial use of a solenoid was disappointing at best, but the consequences of the consequent use of a servo were surprising. We are happy that we did not need to implement a more elaborate control system. It is nice to know that the swing generally worked more or less as we originally intended it to.

Our results exceeded our expectations: we were able to get excellent performance without any additional elaborate software or hardware. We even have an icing on the cake since we will attempt to swing in a full circle during the demo.

For next time, replaced the rigid rods with chains would make the swing more authentic. We could also make the swing prettier and add flare by including buttons to control the maximum amplitude, for example. To make things interesting, we could turn this into a dynamics and feedback problem by creating a swing that starts from a standstill and ends balancing itself upside-down at the top of the swing. Unfortunately, I believe that this interesting project would be outside of the budgetary constraints of the project.

 

Intellectual Property Considerations

Intellectual property is effectively nonexistent in the design of our project. In terms of mechanical design, we built a scale model of a common playground swing, which lacks significant science behind such construction. In terms of electrical and software design, the circuits and code use elementary principles that can be found in any physics textbooks. There are even two other groups this year constructing very similar swings. Therefore, there are no patent opportunities. We did not reuse code, use an existing design, or signed any NDAs.

 

Ethical Considerations

In the context of the IEEE Code of Ethics, all the claims made in this report are supported by the operational swing (Rule 3); we elected not to sell our project to one of the other swing groups (Rule 4); we were qualified to use all tools and components involved in the project (Rule 5); we incited constructive criticism from Bruce, his team of TAs, and fellow students and noted all external contributions (Rule 7); and we encouraged the open use of our power-tools by other groups (Rule 10). 

back to top

 

Special Thank You

We’d like to thank Bruce for the idea itself and his general ability to kick ass and fix all of our problems. We’d like to thank the TA’s, especially Gus wasting multiple hours diagnosing our ignorant problems. Most of all, we’d like to thank Konstantin Klitenik for providing back up servos and for being our personal project consultant in the late stages of the project. Without these people, our swing just would not swing.

 

Appendix

Appendix A: Code

#include <Mega32.h>

 

#define begin {                          

#define end }

#define t1 100

//12 seconds

#define init 44776

//24 seconds

#define init2 89552

 

void initialize(void);//initialization stage

void read(void);//reads ADC and filters input

 

//variable declarations

unsigned char time1,Ain0,Ain1,Ain2,Ain3,Ain4,Ain5,Ain6,Ain7;

unsigned int temp,count;

unsigned char tilt,oldtilt1,oldtilt2,wait,flip,pulsecount,width;

long int initcount;

 

//interrupt drives timing for read() function and times out different

//stages of swing operation

//first stage swings automatically at low amplitude period for 12 seconds

//secod stage swings automatically at medium amplitude period for 12 seconds

//third stage uses sensor to trigger the motor at ideal time

interrupt [TIM0_COMP] void timer0_compare(void)

begin

  //iterate timer variable for read() function    

  time1--;

  //iterate init counter while still in auto mode

  if(initcount <= init2) initcount++;

  //time wait flag to halt operation for number of cycles

  if(wait == 1) count++;

  

  if(initcount >= init2)//sensor mode

  begin

    if(tilt < 195 && tilt <= oldtilt1 && oldtilt1 <= oldtilt2 && wait == 0)//detect extreme postion if not halted by wait flag

    begin

      if(flip == 0)

      begin

        width = 8;    

        PORTD.7 = 0;

        flip = 1;

      end 

      else

      begin

        width = 3;

        PORTD.7 = 1;

        flip = 0;

      end  

      wait = 1;//set wait to halt further action

    end

  end

  else//if not in sensor mode dont detect extreme position, just trigger motor when not halted by wait

  begin

    if(wait == 0)

    begin

      //use flip variable to alternate direction of servo movement

      if(flip == 0)

      begin

        //update pulse width for control line and light LED for debugging

        width = 3;    

        PORTD.7 = 0;

        flip = 1;

      end 

      else

      begin

        width = 8;

        PORTD.7 = 1;

        flip = 0;

      end  

      wait = 1;//set wait to halt further action

    end

  end

 

  //create pulse for servo motor conrol with appropriate width

  if(pulsecount == 74)//74cycles counts up 20ms periods

  begin

    PORTB.0 = 1;

    pulsecount = 0;

  end

  else if (pulsecount == width)

  begin

    PORTB.0 = 0;

  end

  pulsecount++;

 

  if(initcount <= init2)

  begin

    //first stage trigger servo every half low amplitude period

    if(initcount <= init)

    begin

      if(count >= 2487)

      begin

        wait = 0;//resume

        count = 0;

      end

    end

    else//second stage trigger servo every half med amplitude period

    begin

      if(count >= 2568)

      begin

        wait = 0;//resume

        count = 0;

      end

    end  

  end

  else//sensor stage, just prevent rapid triggerings of motor

  begin 

    if(count >= 1200)

    begin

      wait = 0;//resume

      count = 0;

    end   

  end

end

 

void main(void)

begin     

  initialize();

  while(1)

  begin

    if(time1 <= 0) read();//read adc every 100 cycles   

  end

end

//reads ADC ad filters output   

void read(void)

begin

  time1 = t1;

  //store previous 7 values

  Ain7 = Ain6;

  Ain6 = Ain5;

  Ain5 = Ain4;

  Ain4 = Ain3;

  Ain3 = Ain2;

  Ain2 = Ain1;

  Ain1 = Ain0;

  //get new sample

  Ain0 = ADCH;

  //add all samples and divide by 8 to average

  temp = ((unsigned int)Ain7 + (unsigned int)Ain6 + (unsigned int)Ain5 + (unsigned int)Ain4 + (unsigned int)Ain3 + (unsigned int)Ain2 + (unsigned int)Ain1 + (unsigned int)Ain0);

  temp = (temp>>3);

  //store previous two averages for interrupt algorithm  

  oldtilt2 = oldtilt1;

  oldtilt1 = tilt;

  tilt = temp;

  //start another conversion

  ADCSR.6 = 1;

end

 

void initialize(void)

begin

           

   DDRB=0xff;

   DDRD= 0xff; 

   TIMSK=2;       //turn on timer 0 cmp match ISR

   OCR0 = 67;     //set the compare re to 67 time ticks

   TCCR0=0b00001011;    // clock/64 and enable interrupt

   //init count variables

   pulsecount = 0;

   time1 = t1;

   temp = 0;

   flip = 0;

   initcount = 0;

   //init the A to D converter

   //channel zero/ left adj /int Aref  

   ADMUX = 0b01100000;//using Avcc

   //enable ADC

   ADCSR = 0b11000111; 

   //enable interrupts                     

   #asm

      sei

   #endasm

 

end

 

Appendix B: Schematics

High Level Schematic

Optoisolator Schematic

 

Appendix C: Parts List

Parts

Quantity

Cost

Atmel Mega32 Microcontroller

1

8.00

Custom PCB

1

5.00

MMA1260D Accelerometer

1

Sampled

4N35 Optoisolator

1

Free (lab)

Power Supply

2

10.00

Solder Board

1

2.50

Servo Motor

1

10.00

Swing Frame

1

Free (scrap)

Swing Aluminum rods

2

4.00

Swing Hooks

2

1.00

Tungsten Ball

1

Free (lab)

Plexiglas

1

Free (scrap)

Various resistors and capacitors

 

Free (lab)

Various plastic parts and stuff

 

Free (scrap)

TOTAL COST

 

40.50

 

Appendix D: Task Breakdown

Shashank: software design, control algorithm.

Norbert: mechanical design, hardware design.

 

Appendix E: References

Atmel Mega32 Datasheet

Bruce’s Custom Mega32 PCB

FreeScale MMA1260D Accelerometer

4N35 Optoisolator

Background on Swing Physics

 

back to top