예제 #1
0
def activation_radially_from_face(vdw_fname, node_fname, surf_fname,
                                  output_fname, rad, findex, index):

    # Check for problems
    if vdw_fname == None or node_fname == None or surf_fname == None or output_fname == None or rad == None or findex == None:
        raise IOError

    if index == None:
        index = 0
    else:
        index = int(index)

    findex = int(findex)

    # Get FFEA objects
    surf = FFEA_surface.FFEA_surface(surf_fname)
    node = FFEA_node.FFEA_node(node_fname)
    vdw = FFEA_vdw.FFEA_vdw(vdw_fname)

    # Get distance of centroid to core node
    rad = float(rad)
    fcent = surf.face[findex].calc_centroid(node)
    for i in range(surf.num_faces):
        c = surf.face[i].calc_centroid(node)
        if np.linalg.norm(c - fcent) <= rad:
            vdw.set_index(i, index)

    vdw.write_to_file(output_fname)
예제 #2
0
def convert_tet_to_net(input_fnames, output_fname):
    """
    Converts tetgen-compatible files to a netgen-compatible file (which is also
    compatible with FFEA).
    In:
    input fnames : a list of filenames or paths to files for .ele (topology),
    .face (surface) and .node files in the tetgen format.
    output_fname : the name of the desired output file e.g. "output.vol"
    Out:
    nothing in python, but it dumps a file in the working directory.
    """

    # Read files
    top = None
    surf = None
    node = None

    if type(input_fnames) == type(None) or (len(input_fnames) != 3
                                            and len(input_fnames) != 4):
        print("Expected 3 input files! Use --help for help.")
        raise IOError

    for f in input_fnames:
        base = f.rsplit(".", 1)[0]
        ext = f.rsplit(".", 1)[1]

        if ext == "ele":
            top = _FFEA_topology.FFEA_topology(f)

            # Additionally
            if output_fname == "":
                output_fname = base + ".vol"

        elif ext == "node":
            node = _FFEA_node.FFEA_node(f)
        elif ext == "face":
            surf = _FFEA_surface.FFEA_surface(f)

    if output_fname == None:
        print(
            "\tOutput filename not found. Creating default output filename...")
        output_fname = splitext(input_fnames[0])[0] + ".vol"
        if exists(output_fname):
            print(
                "\tDefault output filename already exists. Please supply your own filename (which will be overwritten if it exists"
            )
            raise IOError

    # Now, write them all to file
    fout = open(output_fname, "w")
    fout.write("mesh3d\ndimension\n3\ngeomtype\n11\n\n")
    fout.close()

    surf.write_to_file(output_fname)
    top.write_to_file(output_fname)
    node.write_to_file(output_fname)

    fout = open(output_fname, "a")
    fout.write("endmesh\n")
    fout.close()
예제 #3
0
def convert_surface(insfname, outsfname):

    # Check for problems
    if insfname == None or outsfname == None:
        raise IOError

    # Try to build and save based on the file indices. Objects should raise appropriate errors if something is wrong
    surf = FFEA_surface.FFEA_surface(insfname)
    node = FFEA_node.FFEA_node(insfname)
    surf.write_to_file(outsfname, node=node)
예제 #4
0
def check_danger_elements(vol):
    """
    From the volume data file, this function tells the user if there
    are any extremely long, thin elements in the simulation. If so, it returns
    True, if not, false.
    """
    top = _FFEA_topology.FFEA_topology()
    top.load_vol(vol)
    node = _FFEA_node.FFEA_node()
    node.load_vol(vol)
    
    eindex = 0
    dindex = []
    for e in top.element:
        if e.get_smallest_lengthscale(node) < 0.5: #assuming .vol in nm
            print e.get_smallest_lengthscale(node)
            dindex.append(eindex)
        eindex += 1
    if len(dindex)>0:
        return False
    return True
def activate_via_orientation(vdw_fname, node_fname, surf_fname, output_fname,
                             vn, tol, index):

    # Check for problems
    if vdw_fname == None or node_fname == None or surf_fname == None or output_fname == None:
        raise IOError
    if vn == None or len(vn) != 3:
        raise IOError

    if index == None:
        index = 0
    else:
        index = int(index)

    # Build objects
    vdw = FFEA_vdw.FFEA_vdw(vdw_fname)
    node = FFEA_node.FFEA_node(node_fname)
    surf = FFEA_surface.FFEA_surface(surf_fname)

    try:
        # Normalise vn
        vn = np.array([float(i) for i in vn])
        vn *= 1.0 / np.linalg.norm(vn)
        tol = float(tol)

    except (ValueError):
        raise

    # For all faces, if orientation vector is within lim degrees of face normal, activate it
    for i in range(surf.num_faces):

        # Calculate side of plane
        n = surf.face[i].calc_normal(node)
        ang = np.arccos(np.dot(n, vn)) * (180.0 / np.pi)
        if ang <= tol:
            vdw.set_index(i, index)

    # Output
    vdw.write_to_file(output_fname)
예제 #6
0
def activate_via_halfspace(vdw_fname, node_fname, surf_fname, output_fname, vn, vp, index):

	# Check for problems
	if vdw_fname == None or node_fname == None or surf_fname == None or output_fname == None:
		raise IOError
	if vn == None or len(vn) != 3:
		raise IOError
	if vp == None or len(vp) != 3:
		raise IOError

	if index == None:
		index = 0
	else:
		index = int(index)

	# Build objects
	vdw = FFEA_vdw.FFEA_vdw(vdw_fname)
	node = FFEA_node.FFEA_node(node_fname)
	surf = FFEA_surface.FFEA_surface(surf_fname)	

	vn = np.array([float(i) for i in vn])
	vp = np.array([float(i) for i in vp])

	# For each face
	for i in range(surf.num_faces):
		
		# Calculate side of plane
		c = surf.face[i].calc_centroid(node)
		
		pton = c - vp

		if np.dot(pton, vn) >= 0:
			vdw.set_index(i, index)

	# Output
	vdw.write_to_file(output_fname)
예제 #7
0
import sys, os
import FFEA_node, FFEA_pdb

if (len(sys.argv) != 4):
    sys.exit(
        "Usage: python FFEA_map_PDB_to_FFEA.py [INPUT .node] [INPUT .pdb] [INPUT PDB-Node scale]"
    )

# Get args
innode = sys.argv[1]
inpdb = sys.argv[2]
scale = float(sys.argv[3])

# Build structures
node = FFEA_node.FFEA_node(innode)
pdb = FFEA_pdb.FFEA_pdb(inpdb)

# Assuming these are not deformed (volume overlap maximisation may be possible, but this is easier for starters)
# Move both to origin
node.set_pos([0.0, 0.0, 0.0])
pdb.blob[0].frame[0].set_pos([0.0, 0.0, 0.0])

basepdb = "temp.pdb"
targetnode = "temp.node"
mapfname = "pdbtonode.map"
sparsemapfname = "pdbtonode_sparse.map"
node.write_to_file(targetnode)
pdb.write_to_file(basepdb)

# Make the map
예제 #8
0
        # Sort checkpoint files
        os.system("mv " + os.path.dirname(os.path.abspath(inffea)) +
                  "/lol_checkout.fcp " +
                  os.path.dirname(os.path.abspath(inffea)) +
                  "/lol_checkin.fcp")
        script2.write_to_file(outffea, verbose=True)

        # End the viewer
        #viewer_process.kill()

        # Start ffea
        os.system("ffea " + outffea)

# Finished minimisation! Make node files from this trajectory
try:
    traj = FFEA_trajectory.FFEA_trajectory(script2.params.trajectory_out_fname)
    traj.blob[0][0].frame[-1].rescale(1.0 / script2.blob[0].scale)
    traj.blob[1][0].frame[-1].rescale(1.0 / script2.blob[1].scale)
    traj.blob[0][0].frame[-1].write_to_file("blob0_overlap.node")
    traj.blob[1][0].frame[-1].write_to_file("blob1_overlap.node")
except (IOError):
    print("No overlapping performed. Printing out original nodes")
    node = FFEA_node.FFEA_node(script2.blob[0].conformation[0].nodes)
    node.write_to_file("blob0_overlap.node")
    node = FFEA_node.FFEA_node(script2.blob[1].conformation[0].nodes)
    node.write_to_file("blob1_overlap.node")

# Remove all weirdo files
os.system("rm " + os.path.dirname(os.path.abspath(inffea)) + "/lol*")
#  the Free Software Foundation, either version 3 of the License, or
#  (at your option) any later version.
#
#  FFEA 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 FFEA.  If not, see <http://www.gnu.org/licenses/>.
#
#  To help us fund FFEA development, we humbly ask that you cite
#  the research papers on the package.
#

import FFEA_pin, FFEA_node
import sys

if len(sys.argv) != 5:
    sys.exit(
        "Usage: python FFEA_pin_radially.py [INPUT .node] [OUTPUT .pin] [Node to pin about] [Radius]"
    )

# Get args
node = FFEA_node.FFEA_node(sys.argv[1])
pin = FFEA_pin.FFEA_pin(sys.argv[2])
node_index = int(sys.argv[3])
radius = float(sys.argv[4])
pin.pin_radially(node, node_index, radius)
pin.write_to_file(sys.argv[2])
    sys.exit(
        "Usage: python " + os.path.basename(os.path.abspath(sys.argv[0])) +
        " [INPUT .node fname] [OUTPUT .node/.pdb fname] [INPUT ffea .map fname]\n"
    )

# Get args
innode = sys.argv[1]
outfname = sys.argv[2]
inmap = sys.argv[3]

if len(sys.argv) == 5:
    pdbtop = sys.argv[4]
    pdb = FFEA_pdb.FFEA_pdb(pdbtop)

# Get nodes
input_nodes = FFEA_node.FFEA_node(innode)

# Get map
kinetic_map = FFEA_kinetic_map.FFEA_kinetic_map(inmap)

# Apply matrix!
output_nodes = kinetic_map.apply_sparse(input_nodes)

# Print to file
base, ext = os.path.splitext(outfname)

# Finding these values would take to long, so set all to surface as this is just a test script
num_nodes = len(output_nodes)
num_surface_nodes = len(output_nodes)
num_interior_nodes = 0
예제 #11
0
def calculate_element_volumes(top_fname, node_fname, out_fname):

    # Check for problems
    if top_fname == None or node_fname == None:
        raise IOError

    # Get FFEA objects
    node = FFEA_node.FFEA_node(node_fname)
    top = FFEA_topology.FFEA_topology(top_fname)

    # Build tuples of indices and volumes
    index = 0
    tups = []
    for e in top.element:
        tups.append(
            (index, e.calc_volume(node), e.get_smallest_lengthscale(node)))
        index += 1

    # Sort
    sorted_tupsvol = sorted(tups, key=lambda tup: tup[1])
    sorted_tupslen = sorted(tups, key=lambda tup: tup[2])

    # Write
    if out_fname == None:
        out_fname = os.path.splitext(top_fname)[0] + ".dat"


#	if os.path.exists(out_fname):
#		print("Output file already exists\n")
#		raise IOError

    with open(out_fname, "w") as fout:
        fout.write("Index\tVolume\t\t\tIndex\tLength\n\n")
        x1 = []
        y1 = []
        x2 = []
        y2 = []
        for t1, t2 in zip(sorted_tupsvol, sorted_tupslen):
            x1.append(t1[0])
            y1.append(t1[1])
            x2.append(t2[0])
            y2.append(t2[2])
            fout.write("%d\t%e\t\t%d\t%e\n" % (t1[0], t1[1], t2[0], t2[2]))

    # Write important stuff
    print("\nElement Volume Details for '" + top_fname + "':\n")
    print("\tSmallest: Index=%d, Volume=%f, Length=%f" %
          (x1[0], y1[0], top.element[x1[0]].get_smallest_lengthscale(node)))
    print("\tLargest: Index=%d, Volume=%f, Length=%f" %
          (x1[-1], y1[-1], top.element[x1[-1]].get_smallest_lengthscale(node)))
    print("\tAverage: %f +/- %f" % (np.mean(y1), np.std(y1)))

    print("\n\nElement Length Details for '" + top_fname + "':\n")
    print("\tSmallest: Index=%d, Length=%f, Volume=%f" %
          (x2[0], y2[0], top.element[x2[0]].calc_volume(node)))
    print("\tLargest: Index=%d, Volume=%f, Length=%f" %
          (x2[-1], y2[-1], top.element[x2[-1]].calc_volume(node)))
    print("\tAverage: %f +/- %f" % (np.mean(y2), np.std(y2)))

    # Plot
    plt.figure()
    plt.plot(y1)
    plt.ylabel("Element Volumes")
    plt.title("Element Volume Range")
    plt.savefig(os.path.splitext(out_fname)[0] + "_vols.png")

    plt.figure()
    plt.plot(y2)
    plt.ylabel("Element Lengths")
    plt.title("Element Length Range")
    plt.savefig(os.path.splitext(out_fname)[0] + "_lengths.png")
inmatfname = sys.argv[1]
outmatfname = sys.argv[2]
innodefname = sys.argv[3]
intopfname = sys.argv[4]
radius = float(sys.argv[5])
node_index = int(sys.argv[6])
d = float(sys.argv[7])
sv = float(sys.argv[8])
bv = float(sys.argv[9])
sm = float(sys.argv[10])
bm = float(sys.argv[11])
di = float(sys.argv[12])

# Build objects
mat = FFEA_material.FFEA_material(inmatfname)
node = FFEA_node.FFEA_node(innodefname)
top = FFEA_topology.FFEA_topology(intopfname)

# Run sweep and set parameters
central_node = node.pos[node_index]
num_changed = 0
elindex = -1
for el in top.element:
    elindex += 1
    if np.linalg.norm(el.calc_centroid(node) - central_node) < radius:
        mat.set_params(elindex, d, sv, bv, sm, bm, di)
        num_changed += 1

print "Changed " + str(num_changed) + " elements, leaving " + str(
    top.num_elements - num_changed) + " elements as they were."
mat.write_to_file(outmatfname)
예제 #13
0
import sys
import FFEA_node, FFEA_pin
from numpy import linalg

if len(sys.argv) != 9:
    sys.exit(
        "Usage: python FFEA_pin_in_box.py [INPUT .node fname] [OUTPUT .pin fname] [x limits (max min)] [y limits (max min)] [z limits (max min)]"
    )

# Get args
node_fname = sys.argv[1]
pin_fname = sys.argv[2]
limits = [float(sys.argv[i + 3]) for i in range(6)]

# Get nodes and create pinned node object
nodes = FFEA_node.FFEA_node(node_fname)
pinned = FFEA_pin.FFEA_pin(pin_fname)
pinned.reset()

# Set nodal centroid
centroid = [0.0, 0.0, 0.0]
nodes.set_centroid(centroid)

# Pin some nodes!
for i in range(nodes.num_nodes):
    if nodes.pos[i][0] >= limits[0] and nodes.pos[i][0] <= limits[
            1] and nodes.pos[i][1] >= limits[2] and nodes.pos[i][1] <= limits[
                3] and nodes.pos[i][2] >= limits[4] and nodes.pos[i][
                    2] <= limits[5]:
        pinned.add_node(i)