Sign in to follow this  
Followers 0
Michael Lloyd

Tank vapor out flow calc

12 posts in this topic

I was asked to come up with a way to measure the total "exhausted vapor flow rate per day" from a tank. That might not sound too difficult on first glance but there's more to the story. I'm going to describe what I need to do and hopefully get some good ideas. If nothing else the action of writing all of this stuff may trigger an idea or two... They want this done for LACT units (Lease Acquisition and Custody Transfer). A LACT is used to measure crude oil. Typically ours have (2) 400 Bbl tanks, a measurement skid, and a 500 BPH LACT pump that's controlled by a tank level transmitter. LACT pump off setting is usually 3' and LACT pump on is usually 5' (sometimes 4). Each LACT will typically have two truck loading stations that will accommodate 4 trucks (2 each). I'm going to make this an AOI to make it easier to use (this project is what got me back on a mission to use string tags in AOI's). I'll probably use ladder to make it simpler to edit. Here's the deal... Once the trucks stop pumping, in the tank level will drop to 3' and the LACT pump shuts down. This is the zero point, baseline, whatever... When a truck starts to unload into the tank, the level in the tank starts to rise. At the point in time where it starts to rise I need to begin to monitor the level (I'm thinking a compare and timer with a set coil). We'll call this start level. At a level of 6' in the tank the pump comes on and depending on a number of conditions (listed later) the level will either rise or fall. If it begins to fall then I need to trigger a measurement and store it. Stop minus start = footage changed. Increment a counter (I'm thinking that the counter will be an indirect address pointer to an array tag.). Then wait for the level to stop falling <--- this is not necessarily going to be pump stop Condition one- there is only one truck on the rack and his pump cannot pump in as fast as ours pumps out, the level begins to drop, the program grabs the footage level and calculates total footage into the tank Condition two- there is only one truck on the rack but his pump can pump in as fast as ours pumps out, the level continues to rise but at a slower rate. Once the level begins to fall the program grabs the footage level and calculates total footage into the tank Condition three- There are a lot of variations of this condition so I'll try to summarize. If another truck or trucks connects and start to pump then, depending on where in the cycle they start to pump, the rate could either continue to rise faster or (most important) cause the decreasing rate of change to switch to increasing rate of change which would trigger another measurement cycle. There are many variations of this scenario up to and including 4 trucks arriving and leaving at the same time to staggered arrival/departure, to all kind of variation in between. I only need to accumulate positive changes in level. If the level is falling I don't worry about. If its falling and then changes direction I have to grab the start level and then grab the stop level when it starts to descend. At the end of 24hours I want to have a total accumulated footage. That will tell the engineers how much vapor (not counting boiling, that's another calc that's actually a lot easier to pull off than this) is displaced from the tank during a 24 hour period. I've been trending the tank levels at the first station that I need to implement this. It looks like this: X axis is 2 hours. Y axis is 0-20 feet. Sample rate is 500ms I attached a screenshot of the trend running my laptop. The colors Red and Magenta are for the tanks on one LACT. Green and Blue are for another. White for another. Cyan for another. Some of the levels track together and some don't. The first two LACTs listed have a transmitter in each tank. The last two only have one transmitter for both tanks.

Share this post


Link to post
Share on other sites
So is what you are really after is an accumulator of the positive rate of change in level? Create a rate of change piece of code eg Sample every second and compare with the value taken 10 seconds ago If the value is > 0 then oneshot Capture the current level (Captures the start level) If value is < 0 then oneshot Capture the current level (Capture the finish level) oneshot Totaliser = totaliser + (Finish level - Start level) Others can help with getting the rate of change code more accurate if needed

Share this post


Link to post
Share on other sites
You need flowmeters in and out, a tank-level to volume lookup chart. Add a little subtraction to estimate vented vapor losses. If you can't know or accurately model the inflow and outflow and they can occur simultaneously, I think you will be chasing your tail.

Share this post


Link to post
Share on other sites
So If I read your process correctly what you are wanting is the volume of vapor expelled from the tank daily. Your assumption is that any positive increase in tank volume means that a corresponding volume of vapor was expelled. if that's true then MichaelG's approach with a slight modification will work. This of course assumes that the pressure of your vapor is greater than atmospheric pressure. To be more accurate you'd need to monitor pressure in the exhaust pipe and measure your level change when greater than 14.5 psi. But your rounds are probably close enough for what you're doing.

Share this post


Link to post
Share on other sites
To simplify the post I'll reply to Bob's post and that should cover everyone else. This is correct Bob. Okie I have no way to know the inflow rate. Outflow I know with good precision because we have coriolis or PD meters and Omni flow computers on each LACT. Since I'm only monitoring the positive change cycles I don't really care how much enters or leaves, I just need to know the "evacuated space". As for the need to know RVP, etc of the fluid that's for another time. API-42 has all of the equations that make the EPA happy and at first look it doesn't seem to be too difficult to implement the equations in an AOI. Hopefully I can find some time this week to get something coded up and in the PLC. Next week I have to suffer through being in Big Bend for 4 days. No cell phone service in most locations. Limited wifi in the restaurant. Wide open spaces. Ick... it's like being on vacation (because it is). I might even have to sit back and watch the sun set over a canyon... Edited by Michael Lloyd

Share this post


Link to post
Share on other sites
I am thinking the same lines as Bob's way, compare to last reading and log the rate/duration of positve change. Wow that sounded simple! I'd like to see the finished product and the solution! Hope your able to survive Big Bend!

Share this post


Link to post
Share on other sites
Okay, I think I understand what you're set up looks like now and you have the math under wraps for the tank math, one unknowable variable (in flow) which you need to eliminate mathematically and cumulatively. EDIT: Rewritten from here again: You should be able to take textbook formulae and translate to control logic as long as you properly account for the time issue in translation...You need a totalizer optimized for Logix5k using a periodic task and/or the built in TOT function. You need to calculate change in volume as a model to compare against known outflow and when an error between what you modelled with the outflow meter deviates in either direction from what you measure, then you...uh...that's where I'd be stumped without another constraint...Is the evaporation rate available in the formulae, and you need to verify that? Is the pressure monitored and or otherwise calculable? EDIT: If this also applies to the use of a string tag in AOI thread read on... Instead of using an AOI with the limitations you've bumped up against, perhaps this is better suited for a good old fashioned subroutine (with/without parameters) and an array of UDTs? You can't always encapsulate everything into tidy little packages, and sometimes it's better not to go too far away from generic proven logic. Edited by OkiePC

Share this post


Link to post
Share on other sites
For some reason I'm not getting reply notifications... Flow is irrelevant for what the engineer wants. He only needs the cumulative positive level changes over a 24 hour period. If the tank level goes up 4', store in Z and continue. If it's declining... nothing gets done. Once the level changes direction to increasing. Place a value in Y. Watch the level, when it changes direction to decreasing (some dead band will have to be applied for direction changes. Probably with a time delay), place a value in X. Calc Z= Z + (X-Y) and do it a gain... I have a lot of tanks in a lot of different PLC's to apply this to. It's perfect for an AOI. I don't think I'll mess with the String tags in AOI's anymore. It's not that valuable and I've been living without them for a couple of years now. Besides that, it can't be done like I need it to be done. I use Strings where I can.

Share this post


Link to post
Share on other sites
I will suffer through Big Bend. Woe is me...

Share this post


Link to post
Share on other sites
Done and it works as desired. There wasn't all that much to it but it looks a little different than what was suggested because I wrote it in ladder. The basic premise is there. Once I tested it in ladder I converted it to an AOI for portability, I attached the AOI in zip format. I wrote it for a Rev 19 controller. TVVDC.zip

Share this post


Link to post
Share on other sites
Michael looks like quite elegant from what I can see and understand withn a quick once over. Glad you were successful. If I may offer 2 cents - The CLGX supports up to 64 characters in a tag name. Don't hesitate to use a few more characters and make your tag names meaningful. Today we know Ht probably is height. and CSU is Count System Up and CSD is Count System Down. But in five years we'll scratch our heads to figure out what these tag names mean. Just a simple observation that code looks quite elegant.

Share this post


Link to post
Share on other sites
Thank you Bob. I try to write things as compact and simple as I can. At one time I probably stretched the bounds of AB's character limits for tags. Now I document my tags as clearly as I can, though I could have been more clear with the AOI documentation, and try to keep tag length as short as I can. Why? Because every character typed represents time spent typing and I do a lot of typing in the PLC that keeps me from typing in the HMI as it is. Actually, it's not just for me, it's also for the guy writing the HMI (which is often me). Here's an example of my analog alarm block tag. I think the tags are clear and concise. Everything that the program, HMI, and even tech could need for an analog input point lives in this tag. One of the people that used to do HMI work for me thought that I was too wordy with this particular UDT. The guy that I work with now thinks they make sense and has created an embedded object in ClearSCADA so that adding an analog is a drag and drop operation. You win some and you lose some. My coworker and I have both spent time working with DCS architecture so maybe that's the difference. That said, I could have been more clear with the tags that I used in the AOI. Note the string tags. The text shows up on a faceplate that pops up when you click on the process variable in the HMI. The EnableAlarms enable/disable visibility attributes in the HMI as well as functionality in the PLC. I do most of the docs in Excel (CSV) and import. I've got a "template" that I change the PT-2010 (for example) to PT-2012 and it changes it in the rest of the descriptions. I always start with an IO sheet and document the program by cutting and pasting the docs to the exported CSV file. I have a "blank" program with one of each card defined and documented with "spare" so that as I drag a card from the blank to the working the docs come with it. I call my analog alarm routine (I wrote my own. I hate AB's) with a loop and scale on the card. I set the number of analogs to call and a few parameters in the Analog tag with a file I call IOM (IO map). zHere's a piece of that code: Index_Max_Analog := 88; Analog[0].PV := Local:9:I.Ch0Data; Analog[0].MinEU := Local:9:C.Ch0Config.LowEngineering; Analog[0].MaxEU := Local:9:C.Ch0Config.HighEngineering; Analog[1].PV := Local:9:I.Ch1Data; Analog[1].MinEU := Local:9:C.Ch1Config.LowEngineering; Analog[1].MaxEU := Local:9:C.Ch1Config.HighEngineering; When I have 100+ this would seem to be daunting to type. Nope... I have an excel sheet where I define the card parameters in a few cells and the tags are created from that. Then I copy and paste to the STX file. The spreadsheet is a work in progress but for now it lets me map 200 analogs in about 5 minutes. I'm working on motors and valves but there isn't much to them and I'm busier than a cat covering up poop on a hot rock right now so there isn't much time to play. Sorry about that... I didn't mean to branch off into design philosophy. I'm off to Big Bend when I hit Add Reply. Have a great week

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0