Linearizing an LED for 800 pwm steps'?


Closed Thread
Results 1 to 37 of 37

Hybrid View

  1. #1
    Join Date
    Mar 2009
    Posts
    653

    Default Linearizing an LED for 800 pwm steps'?

    Hi there...long time no post, dusted my pic stuff down & have dived straight back in....almost out the blocks I'm stumbling - not with the picbasic aspect but maths, logs etc! (knew I should have paid more attention in maths classes!)

    Anyway, I want to fade an LED up & down so it appears linear to the eye ...if I just step the LED linearly, my eye (& I guess everybody elses eyes!), sees the main brightness changes at the lower end of the stepping scale (so for example with 256 bits....the main visual brightness steps happen at the lower end of the range 0-50 ....with less perceivable change in steps as you head on up to 255 bits)....the end result is a lumpy fade up/down.

    Now then, I need to use a PWM frequency of about 20khz (in case you're wondering the LED still seems to react ok at this frequency!) ...this is beacause the LED will be going into an audio circuit & past attempts have proved that the PWM signal bleeds into the signal very easy so low PWM frequencies are out ...the kludge is to put it above the hearing range of most......at 16Mhz, a 20khz signal gives 800 bits of resolution, so what I'm wanting is for some maths savvy person to give me a hint at how I would use a LUT for 800 values in a way that would make the LEDappear to be fading up/down linearly?

    Any ideas?

  2. #2
    Join Date
    Mar 2009
    Posts
    653


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    Ok...I think I might be stuffed here! (it won't be the first time!)

    I'm using a lowly 12f1840 (as I need to use a PIC with just 8 pins -due to physical space constraints!) .....am I right in thinking that below the the PIC18F series ...I can't use a lookup table with more than 256 entries? (because as it turns out, I think I need a lookup table with 1024 entries!)
    Last edited by HankMcSpank; - 26th February 2012 at 17:10.

  3. #3
    Join Date
    Nov 2005
    Location
    Bombay, India
    Posts
    967


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    Hi Hank

    Why 800 or even 1024 steps? Why not 256? You may need even lesser!!!
    Yes the lookup table approach is appropriate. However, since the majority brighness changes happen in the bottom segment, you need a very tiny step size/value changes at those levels. The easiest way to create this table of PWM values is to take your favourite desktop programming language and write a small program that will print out the PWM values. I have been used to using QuickBasic from MS for such stuff.

    Code:
    j = 1
    for i = 0 to 256 step j                ' keep widening the step size as we don't need high resolution at larger PWM values
        print log(i)*256;",";               ' print a value like this "val,"  and stay on the line
        j = j+1
    next
    This, of course, is not the best code, but, just a guideline to get you moving.

    Regards

  4. #4
    Join Date
    Mar 2009
    Posts
    653


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    thanks ...i know how to do 256 steps....the problem is it's not enough resolution

    I likely need 1024 steps (even a pwm value of 1 has the led quite visible).....at 256 steps a PWM value of 1 is too bright.

    I can obviously just use 1024 steps and drive the LED that way ...but without some form of linearizing lookup/data table the LED doesn't fade up/down smoothly (all the brightness action is slanted towards the lower end of the PWM scale)

    i've since worked out how to generate the curves I need....but what I still can't figure out is how to put this resulting lookup data into code space.

    I read Melanie's "use code space as your playground"....but her syntax relates to PBP assembler....and I'm too clueless to map it to MPASM!

    I tried pokecode....but it baulked when the data lookup values got above 255.

    Since I can't use Lookup2 .....all I want to do is (for a starter!) get the following 512 lookup values into my program/codespace (my PIC has 7KB of program space ...my program is only about 1800 words...so should be sufficient space to cram list of 512 words in)....

    Code:
    0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,
    50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,
    96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,
    131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,
    165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,
    199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,
    233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,
    267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,
    301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,
    335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,
    370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,
    405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,
    441,442,443,444,445,446,447,448,449,450,451,452,453,454,455,456,457,458,459,460,461,462,463,464,465,466,467,468,469,470,471,472,473,474,475,476,
    477,478,479,480,481,482,483,484,485,486,487,488,489,490,491,492,493,494,495,496,497,498,499,500,501,502,503,504,505,506,507,508,509,510,511
    Just to give a little more detail wrt the end goal - I'm wanting to take an AD reading & convert it to LED brightness ....I'm using 10 bit ADC...so my intention is to divide the AD result by two then use that AD value to reference the corresponding bit of 512 words in that list ....therefore if incoming AD reading is 760 (10 bit reading)....divide it by 2 to get a 9 bit reading of 380 .....now reference the for 380th entry in that sequence of values ...that'll be the PWM value I need to use.


    I've been searching/reading all night & I'm as confused now as whe I started - is this even do-able?
    Last edited by HankMcSpank; - 27th February 2012 at 01:50.

  5. #5
    Join Date
    Apr 2007
    Location
    Pennsylvania, USA
    Posts
    158


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    Could you do something like this?

    Code:
    ADCvalue var word
    x        var byte
    duty     var byte
    
    main:
    adcin 0, ADCvalue
    x=adcvalue/2
    
    if x<256 then lookup x, [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,_
    50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,_
    96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,_
    131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,_
    165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,_
    199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,_
    233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255],duty
    
    if x>255 then lookup x, [256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,_
    301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,_
    335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,_
    370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,_
    405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,_
    441,442,443,444,445,446,447,448,449,450,451,452,453,454,455,456,457,458,459,460,461,462,463,464,465,466,467,468,469,470,471,472,473,474,475,476,_
    477,478,479,480,481,482,483,484,485,486,487,488,489,490,491,492,493,494,495,496,497,498,499,500,501,502,503,504,505,506,507,508,509,510,511],duty
    
    hpwm 1, duty, 1000
    
    goto main
    Shawn

  6. #6
    Join Date
    Nov 2005
    Location
    Bombay, India
    Posts
    967


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    of course it is do-able. However, I don't think you'll be too happy with the linearity. I am currently working with a similar led lighting problem and know what you're talking about. You need very fine grain at the bottom of the curve to get the intensity variations you need. Shawn has shown an excellent way to split the table lookup into 2 parts.

  7. #7
    Join Date
    Feb 2006
    Location
    Gilroy, CA
    Posts
    1,530


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    Hi Hank,

    What kind of math did you use for your excel graph? Wondering if we can get close to that without a lookup.
    http://www.scalerobotics.com

  8. #8
    Join Date
    Mar 2009
    Posts
    653


    Did you find this post helpful? Yes | No

    Default Re: Linearizing an LED for 800 pwm steps'?

    Quote Originally Posted by ScaleRobotics View Post
    Hi Hank,

    What kind of math did you use for your excel graph? Wondering if we can get close to that without a lookup.
    It wasn't that slick...nor scientific - basically I was after an anti log type of slope...now when it comes to maths & trig, I'm an epic fail - the only excel function I could get to work was Excel's 'log' (I'm not particularly familiar with excel either!), so I simply dragged down the rows to 512 - applied the log formula (log (A1,512) ...which gave me all the log values ....I then inverted the result in Excel (there's got to be a better way, but I work with the tool & knowledge constraints I have - I don't have time each time I hit a problem to park up & learn how to do it the right way!)

    So basically it's an anti log.....but I'd imagine doing the calculation in in PBP, would be like having your kneecaps drilled, then filled with salt & vinegar.

Members who have read this thread : 0

You do not have permission to view the list of names.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts