#!/usr/bin/python3
# -*- coding: utf-8 -*-
'''Pychemqt, Chemical Engineering Process simulator
Copyright (C) 2009-2025, Juan José Gómez Romera <jjgomera@gmail.com>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
Neumatic conveying is a way that bulk solids can be pumped from one location to
another suspended in a flowing gas. Pneumatic conveying of bulk solids is
widely used in the process industry, such as food, pharmaceuticals, fine
chemikcal, paper pulp, fertilizer, cement or metal ores.
Its advantages includes:
* Enclosure of bulk product avoiding mechanical incident, fire or
explosion risk. Avoid too contamination of material
* Saving space as the conveying line can be above ground.
* Automation fairly easy
Its disadvantages includes:
* Abrasive materials can be erosive pipes and other equipment coming into
contact with the product
* Particles must be dry
* Friable materials have particle breakage
* Material that oxidize easily need a inert gas as carrier fluid
Any pneumatic conveying systems have this basic components:
* The gas mover, equipment like a blowers, a centrifugal fans or a
reciprocating compressors
* The transport pipeline
* Product-Gas separador like a cyclone, filter or settling chamber
'''
from math import pi
from equipment.parents import equipment
from lib.drag import terminalVelocity
from lib.friction import f_friccion
from lib.neumatic import V_saltation, f_solid
from lib.unidades import Pressure, Speed
from tools.qt import translate
[docs]
class Neumatic(equipment):
"""Class to define the pneumatic conveying equipment
Parameters:
entrada : Corriente instance to define the input stream to equipment
D : Pipe diameter
orientation : Geometric orientation of pipe
0 - Horizontal
1 - Vertical
saltation : Method to calculate saltation velocity of gas:
0 - Kizk (1973)
1 - Matsumoto (1977)
2 - Matsumoto (1975)
3 - Matsumoto (1974)
4 - Ochi (1991)
fs : Method to calculate solid friction factor
0 - Stemerding (1962)
1 - Reddy-Pei (1969)
2 - Swaaij-Buurman-Breugel (1970)
3 - Capes-Nakamura (1973)
4 - Konno-Saito (1969)
5 - Yang (1978)
eD : Pipe roughness, optional for Ochi saltation velocity method
L : Pipe length
K : Equivalent length of pipe fittings
"""
title = translate("equipment", "Penumatic conveying")
help = ""
kwargs = {
"entrada": None,
"orientation": 0,
"D": None,
"eD": None,
"L": None,
"K": 0,
"saltation": 0,
"fs": 0}
kwargsInput = ("entrada", )
kwargsValue = ("D", "L", "K", "eD")
kwargsList = ("saltation", "orientation", "fs")
calculateValue = ("SLR", "DR", "VF", "vs", "V", "Re", "f", "DeltaP")
TEXT_ORIENTATION = ("Horizontal", "Vertical")
TEXT_SALTATION = ("Kizk", "Matsumoto 1977", "Matsumoto 1975",
"Matsumoto 1974", "Ochi")
TEXT_FS = ("Stemerding", "Reddy-Pei", "Swaaij-Buurman-Breugel",
"Capes-Nakamura", "Konno-Saito", "Yang")
@property
def isCalculable(self):
if not self.kwargs["entrada"]:
self.msg = translate("equipment", "undefined input")
self.status = 0
return
if not self.kwargs["D"]:
self.msg = translate("equipment", "undefined pipe diameter")
self.status = 0
return
if not self.kwargs["L"]:
self.msg = translate("equipment", "undefined pipe length")
self.status = 0
return
self.msg = ""
self.status = 1
return True
[docs]
def calculo(self):
entrada = self.kwargs["entrada"]
# Solid loading ratio (SLR), ratio of the mass flow rate of solids to
# the mass flow rate of gas
self.SLR = entrada.solido.caudal/entrada.Gas.caudalmasico
# Density ratio (DR), ratio of solids density to gas density, normally
# in the order 500-1000
self.DR = entrada.solido.rho/entrada.Gas.rho
# Volume fraction (VF), the ratio of the volume occupied by solids to
# the volume occupied by the gas
self.VF = entrada.solido.Q/entrada.Q
self.eps = 1-self.VF
# Global density
self.rho_ap = entrada.Gas.rho*self.eps
# Saltation velocity calculation
# Set argument set as each method needs
# All methods needs massflow, Dp, rhog and pipe diameter
args = [entrada.solido.caudal,
entrada.solido.diametro_medio,
entrada.Gas.rho,
self.kwargs["D"]]
vt = terminalVelocity(entrada.solido.diametro_medio,
entrada.solido.rho,
entrada.Gas.rho, entrada.Gas.mu)
area = pi/4*self.kwargs["D"]**2
self.V = Speed(entrada.Gas.Q/area)
self.Re = self.V*self.kwargs["D"]/entrada.Gas.nu*entrada.Gas.rho
self.f = f_friccion(self.Re, eD=self.kwargs["eD"])
# Matsumoto methods needs too solid density and terminal velocity
if self.kwargs["saltation"] in (1, 2, 3):
args.append(entrada.solido.rho)
args.append(vt)
# Ochi method need too terminal velocity and darcy friction factor
if self.kwargs["saltation"] == 4:
args.append(vt)
args.append(self.f)
self.vs = V_saltation(self.kwargs["saltation"], *args)
# Solid friction factor calculation
if self.kwargs["orientation"] == 1:
# Horizontal pipe
eps = 0
self.fs = fs_Yang_Horizontal(eps, self.V, self.kwargs["D"])
else:
# Vertical orientation
args = []
if self.kwargs["fs"] != 0:
args.append(self.vs)
if self.kwargs["fs"] == 4:
args.append(self.kwargs["D"])
if self.kwargs["fs"] == 5:
args.append(0) # eps
args.append(vt)
args.append(self.V)
self.fs = f_solid(self.kwargs["fs"], *args)
DeltaP_ac = self.kwargs["K"]*self.V**2/2*entrada.Gas.rho
DeltaP_f = self.kwargs["L"]*self.V**2/self.kwargs["D"]*self.f*entrada.Gas.rho/2
self.DeltaP = Pressure(DeltaP_ac + DeltaP_f)
self.salida = [entrada.clone(P=entrada.P-self.DeltaP)]
if __name__ == "__main__":
from lib.solids import Solid
from lib.corriente import Corriente
dm = [17.5e-6, 22.4e-6, 26.2e-6, 31.8e-6, 37e-6, 42.4e-6, 48e-6, 54e-6,
60e-6, 69e-6, 81.3e-6, 96.5e-6, 109e-6, 127e-6]
fracciones = [0.02, 0.03, 0.05, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1,
0.05, 0.03, 0.02]
sol = Solid(caudalSolido=[0.1], distribucion_diametro=dm,
distribucion_fraccion=fracciones, solids=[638])
kw = {"ids": [475], "fraccionMolar": [1.], "MEoS": True}
entrada = Corriente(T=300, P=1e5, caudalMasico=1, solido=sol, **kw)
neumatic = Neumatic(entrada=entrada, D=0.25, eD=0, saltation=4, L=50)
print(neumatic.status, neumatic.msg)