mirror of
https://github.com/JuliaFEM/JuliaFEM.jl.git
synced 2026-08-06 04:21:33 +00:00
Fix documentation
Update documentation of several functions to match documentation guide.
This commit is contained in:
Binary file not shown.
|
After Width: | Height: | Size: 6.8 KiB |
+12
-2
@@ -9,11 +9,21 @@ type Element{E<:AbstractBasis}
|
||||
properties :: E
|
||||
end
|
||||
|
||||
""" Construct a new element of type E.
|
||||
"""
|
||||
Element(element_type, connectivity_vector)
|
||||
|
||||
Construct a new element where element_type is the type of the element
|
||||
and connectivity_vector is the vector of nodes that the element is connected to.
|
||||
|
||||
Examples
|
||||
--------
|
||||
julia> element = Element(Tri3, [1, 2, 3])
|
||||
In the example a new element (E in the figure below) of type Tri3 is created.
|
||||
This spesific element connects to nodes 89, 43, 12 in the finite element mesh.
|
||||
|
||||
```@example
|
||||
element = Element(Tri3, [89, 43, 12])
|
||||
```
|
||||

|
||||
"""
|
||||
function Element{E<:AbstractBasis}(::Type{E}, connectivity::Vector{Int})
|
||||
return Element{E}(-1, connectivity, [], Dict(), E())
|
||||
|
||||
@@ -24,12 +24,16 @@ function xmffile(xdmf::Xdmf)
|
||||
return xdmf.name*".xmf"
|
||||
end
|
||||
|
||||
""" Initialize a new Xdmf object. """
|
||||
"""
|
||||
Xdmf(name, version="3.0", overwrite=false)
|
||||
|
||||
Initialize a new Xdmf object.
|
||||
"""
|
||||
function Xdmf(name::String; version="3.0", overwrite=false)
|
||||
xdmf = new_element("Xdmf")
|
||||
h5file = "$name.h5"
|
||||
xmlfile = "$name.xmf"
|
||||
|
||||
|
||||
if isfile(h5file)
|
||||
if overwrite
|
||||
info("Result file $h5file exists, removing old file.")
|
||||
@@ -38,7 +42,7 @@ function Xdmf(name::String; version="3.0", overwrite=false)
|
||||
error("Result file $h5file exists, use Xdmf($name; overwrite=true) to rewrite results")
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
if isfile(xmlfile)
|
||||
if overwrite
|
||||
info("Result file $xmlfile exists, removing old file.")
|
||||
@@ -55,7 +59,11 @@ function Xdmf(name::String; version="3.0", overwrite=false)
|
||||
return Xdmf(name, xdmf, hdf, 1, "HDF")
|
||||
end
|
||||
|
||||
""" Return the basic structure of Xdmf document. Creates a new TemporalCollection if not found.
|
||||
"""
|
||||
get_temporal_collection(xdmf)
|
||||
|
||||
Return the basic structure of Xdmf document.
|
||||
Creates a new TemporalCollection if not found.
|
||||
Basic structure for XML part of Xdmf file is
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Xdmf xmlns:xi="http://www.w3.org/2001/XInclude" Version="2.1">
|
||||
@@ -79,7 +87,10 @@ function get_temporal_collection(xdmf::Xdmf)
|
||||
return grid
|
||||
end
|
||||
|
||||
""" Returns some spesific child xml element from a array of XMLElement based on,
|
||||
"""
|
||||
xdmf_filter(child_elements, child_name)
|
||||
|
||||
Returns some spesific child xml element from an array of XMLElement based on,
|
||||
"Xdmf extensions" see [1] for details.
|
||||
|
||||
Parameters
|
||||
@@ -93,8 +104,8 @@ Returns
|
||||
-------
|
||||
nothing if nothing is found, otherwise XMLElement matching to filtering
|
||||
|
||||
Examples
|
||||
--------
|
||||
#Examples
|
||||
|
||||
julia> grid1 = new_element("Grid")
|
||||
julia> add_text(grid1, "I am first grid")
|
||||
julia> grid2 = new_element("Grid")
|
||||
@@ -176,8 +187,13 @@ function xdmf_filter(child_elements, child_name)
|
||||
return nothing
|
||||
end
|
||||
|
||||
""" Traverse XML path. Xdmf filtering can be used, so it's possible to find
|
||||
data from xml using syntax e.g.
|
||||
"""
|
||||
traverse(xdmf, x, attr_name)
|
||||
|
||||
Traverse XML path. Xdmf filtering can be used, so it's possible to find
|
||||
data from xml using syntax e.g.
|
||||
|
||||
#Example
|
||||
|
||||
julia> traverse(xdmf, x, "/Domain/Grid[2]/Grid[@Name=Frame 1]/DataItem")
|
||||
"""
|
||||
@@ -203,12 +219,17 @@ function traverse(xdmf::Xdmf, x::XMLElement, attr_name::String)
|
||||
new_path = join(items[2:end], '/')
|
||||
return traverse(xdmf, new_item, new_path)
|
||||
end
|
||||
|
||||
|
||||
child = xdmf_filter(childs, attr_name)
|
||||
return child
|
||||
end
|
||||
|
||||
""" Read data from Xdmf file.
|
||||
"""
|
||||
read(xdmf, path)
|
||||
|
||||
Read data from Xdmf file.
|
||||
|
||||
#Example
|
||||
|
||||
Traversing is supported, so one can easily traverse XML tree e.g.
|
||||
julia> read(xdmf, "/Domain/Grid/Grid[2]/Geometry")
|
||||
@@ -230,7 +251,11 @@ function read(xdmf::Xdmf, path::String)
|
||||
end
|
||||
end
|
||||
|
||||
"""
|
||||
save!(xdmf)
|
||||
|
||||
Save the xdmf file.
|
||||
"""
|
||||
function save!(xdmf::Xdmf)
|
||||
doc = XMLDocument()
|
||||
set_root(doc, xdmf.xml)
|
||||
@@ -264,7 +289,11 @@ function new_dataitem{T,N}(xdmf::Xdmf, path::String, data::Array{T,N})
|
||||
return dataitem
|
||||
end
|
||||
|
||||
""" Create a new DataItem element, hdf path automatically determined. """
|
||||
"""
|
||||
new_dataitem(xdmf, data)
|
||||
|
||||
Create a new DataItem element, hdf path automatically determined.
|
||||
"""
|
||||
function new_dataitem{T,N}(xdmf::Xdmf, data::Array{T,N})
|
||||
if xdmf.format == "XML"
|
||||
# Path can be whatever as XML format does not store to HDF at all
|
||||
@@ -298,10 +327,12 @@ global const xdmf_element_mapping = Dict(
|
||||
"Wedge15" => "Wedge_15",
|
||||
"Hex20" => "Hex_20")
|
||||
|
||||
""" Write new fields to Xdmf file.
|
||||
"""
|
||||
update_xdmf!(xdmf, problem, time, fields)
|
||||
|
||||
Examples
|
||||
--------
|
||||
Write new fields to Xdmf file.
|
||||
|
||||
#Example
|
||||
|
||||
To write displacement and temperature fields from p1 at time t=0.0:
|
||||
|
||||
@@ -359,7 +390,7 @@ function update_xdmf!(xdmf::Xdmf, problem::Problem, time::Float64, fields::Vecto
|
||||
time_element = new_child(spatial_collection, "Time")
|
||||
set_attribute(time_element, "Value", time)
|
||||
end
|
||||
|
||||
|
||||
# 3.1 make sure that Grid element we found really is SpatialCollection
|
||||
collection_type = attribute(spatial_collection, "CollectionType"; required=true)
|
||||
@assert collection_type == "Spatial"
|
||||
|
||||
+81
-6
@@ -34,7 +34,7 @@ end
|
||||
"""
|
||||
Mesh(m::Dict)
|
||||
|
||||
Create new `Mesh` using data `m`. It is assumed that `m` is in format what
|
||||
Create a new `Mesh` using data `m`. It is assumed that `m` is in format what
|
||||
`abaqus_read_mesh` in `AbaqusReader.jl` is returning.
|
||||
"""
|
||||
function Mesh(m::Dict)
|
||||
@@ -56,16 +56,33 @@ function Mesh(m::Dict)
|
||||
return mesh
|
||||
end
|
||||
|
||||
"""
|
||||
add_node!(mesh, nid, ncoords)
|
||||
|
||||
Add node into the mesh. `nid` is node id and `ncoords` are the node
|
||||
coordinates.
|
||||
"""
|
||||
function add_node!(mesh::Mesh, nid::Int, ncoords::Vector{Float64})
|
||||
mesh.nodes[nid] = ncoords
|
||||
end
|
||||
|
||||
"""
|
||||
add_nodes!(mesh, nodes)
|
||||
|
||||
Add nodes into the mesh.
|
||||
"""
|
||||
function add_nodes!(mesh::Mesh, nodes::Dict{Int, Vector{Float64}})
|
||||
for (nid, ncoords) in nodes
|
||||
add_node!(mesh, nid, ncoords)
|
||||
end
|
||||
end
|
||||
|
||||
"""
|
||||
add_node_to_node_set!(mesh, nid, ncoords)
|
||||
|
||||
Add nodes into a node set. `set_name` is the name of the set and `nids...`
|
||||
are all the node id:s that wants to be added.
|
||||
"""
|
||||
function add_node_to_node_set!(mesh::Mesh, set_name, nids...)
|
||||
if !haskey(mesh.node_sets, set_name)
|
||||
mesh.node_sets[set_name] = Set{Int}()
|
||||
@@ -74,7 +91,12 @@ function add_node_to_node_set!(mesh::Mesh, set_name, nids...)
|
||||
return
|
||||
end
|
||||
|
||||
""" Create a new node set from nodes in element set. """
|
||||
"""
|
||||
create_node_set_from_element_set!(mesh, set_names...)
|
||||
|
||||
Create a new node set from the nodes in an element set. ´set_names...´ are all
|
||||
the set names to be inserted in the function.
|
||||
"""
|
||||
function create_node_set_from_element_set!(mesh::Mesh, set_names::String...)
|
||||
for set_name in set_names
|
||||
set_name = Symbol(set_name)
|
||||
@@ -88,21 +110,43 @@ function create_node_set_from_element_set!(mesh::Mesh, set_names::String...)
|
||||
return
|
||||
end
|
||||
|
||||
"""
|
||||
create_node_set_from_element_set!(mesh, set_name)
|
||||
|
||||
Create a new node set from an element set.
|
||||
"""
|
||||
function create_node_set_from_element_set!(mesh::Mesh, set_name::Symbol)
|
||||
create_node_set_from_element_set!(mesh, string(set_name))
|
||||
end
|
||||
|
||||
"""
|
||||
add_element!(mesh, elid, eltype, connectivity)
|
||||
|
||||
Add an element into the mesh. ´elid´ is the element id, ´eltype´ is the type of
|
||||
the element and ´connectivity´ is the connectivity of the element.
|
||||
"""
|
||||
function add_element!(mesh::Mesh, elid::Int, eltype::Symbol, connectivity::Vector{Int})
|
||||
mesh.elements[elid] = connectivity
|
||||
mesh.element_types[elid] = eltype
|
||||
end
|
||||
|
||||
"""
|
||||
add_elements!(mesh, elements)
|
||||
|
||||
Add elements into the mesh.
|
||||
"""
|
||||
function add_elements!(mesh::Mesh, elements::Dict{Int, Tuple{Symbol, Vector{Int}}})
|
||||
for (elid, (eltype, elcon)) in elements
|
||||
add_element!(mesh, elid, eltype, elcon)
|
||||
end
|
||||
end
|
||||
|
||||
"""
|
||||
add_element_to_element_set!(mesh, set_name, elids...)
|
||||
|
||||
Add elements into the mesh. ´set_name´ is the name of the element set and
|
||||
´elids..´ are id:s of all the elements that wants to be added.
|
||||
"""
|
||||
function add_element_to_element_set!(mesh::Mesh, set_name, elids...)
|
||||
if !haskey(mesh.element_sets, set_name)
|
||||
mesh.element_sets[set_name] = Set{Int}()
|
||||
@@ -110,6 +154,11 @@ function add_element_to_element_set!(mesh::Mesh, set_name, elids...)
|
||||
push!(mesh.element_sets[set_name], elids...)
|
||||
end
|
||||
|
||||
"""
|
||||
copy(mesh)
|
||||
|
||||
Copy the mesh.
|
||||
"""
|
||||
function copy(mesh::Mesh)
|
||||
mesh2 = Mesh()
|
||||
mesh2.nodes = copy(mesh.nodes)
|
||||
@@ -120,6 +169,11 @@ function copy(mesh::Mesh)
|
||||
return mesh2
|
||||
end
|
||||
|
||||
"""
|
||||
filter_by_element_id(mesh, element_ids)
|
||||
|
||||
Filter elements by their id's.
|
||||
"""
|
||||
function filter_by_element_id(mesh::Mesh, element_ids::Vector{Int})
|
||||
mesh2 = copy(mesh)
|
||||
mesh2.elements = Dict()
|
||||
@@ -131,10 +185,20 @@ function filter_by_element_id(mesh::Mesh, element_ids::Vector{Int})
|
||||
return mesh2
|
||||
end
|
||||
|
||||
"""
|
||||
filter_by_element_set(mesh, set_name)
|
||||
|
||||
Filter elements by an element set.
|
||||
"""
|
||||
function filter_by_element_set(mesh::Mesh, set_name)
|
||||
filter_by_element_id(mesh::Mesh, collect(mesh.element_sets[set_name]))
|
||||
end
|
||||
|
||||
"""
|
||||
create_element(mesh, id)
|
||||
|
||||
Create an element from the mesh by it's id.
|
||||
"""
|
||||
function create_element(mesh::Mesh, id::Int)
|
||||
connectivity = mesh.elements[id]
|
||||
element_type = getfield(JuliaFEM, mesh.element_types[id])
|
||||
@@ -144,6 +208,11 @@ function create_element(mesh::Mesh, id::Int)
|
||||
return element
|
||||
end
|
||||
|
||||
"""
|
||||
create_elements(mesh, element_type=nothing)
|
||||
|
||||
Create elements from the mesh filtered by their type.
|
||||
"""
|
||||
function create_elements(mesh::Mesh; element_type=nothing)
|
||||
element_ids = collect(keys(mesh.elements))
|
||||
if element_type != nothing
|
||||
@@ -177,7 +246,11 @@ function create_elements(mesh::Mesh, element_sets::AbstractString...; element_ty
|
||||
end
|
||||
|
||||
|
||||
""" find npts nearest nodes from mesh and return id numbers as list. """
|
||||
"""
|
||||
find_nearest_nodes(mesh, coords, npts=1; node_set=nothing)
|
||||
|
||||
find npts nearest nodes from the mesh and return their id numbers as a list.
|
||||
"""
|
||||
function find_nearest_nodes(mesh::Mesh, coords::Vector{Float64}, npts::Int=1; node_set=nothing)
|
||||
dist = Dict{Int, Float64}()
|
||||
for (nid, c) in mesh.nodes
|
||||
@@ -197,9 +270,11 @@ function find_nearest_node(mesh::Mesh, coords::Vector{Float64}; node_set=nothing
|
||||
end
|
||||
|
||||
"""
|
||||
Apply new node ordering to elements. In JuliaFEM same node ordering is used
|
||||
than in ABAQUS and if mesh is parsed from FEM format with other node ordering
|
||||
this can be used to reorder nodes.
|
||||
reorder_element_connectivity!(mesh, mapping)
|
||||
|
||||
Apply a new node ordering to elements. JuliaFEM uses the same node ordering as
|
||||
ABAQUS. If the mesh is parsed from FEM format with some other node ordering,
|
||||
this function can be used to reorder the nodes.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
|
||||
@@ -3,6 +3,13 @@
|
||||
|
||||
using AbaqusReader
|
||||
|
||||
"""
|
||||
abaqus_read_mesh(fn::String)
|
||||
|
||||
Read and parse ABAQUS `.inp` file.
|
||||
|
||||
`fn` (filename) is the name of the file to parse.
|
||||
"""
|
||||
function abaqus_read_mesh(fn::String)
|
||||
m = AbaqusReader.abaqus_read_mesh(fn)
|
||||
return Mesh(m)
|
||||
|
||||
+60
-20
@@ -8,7 +8,7 @@ abstract type MixedProblem<:AbstractProblem end
|
||||
|
||||
"""
|
||||
General linearized problem to solve
|
||||
(K₁+K₂)Δu + C1*Δλ = f₁+f₂
|
||||
(K₁+K₂)Δu + C1'*Δλ = f₁+f₂
|
||||
C2Δu + D*Δλ = g
|
||||
"""
|
||||
type Assembly
|
||||
@@ -81,37 +81,59 @@ function isempty(assembly::Assembly)
|
||||
return T
|
||||
end
|
||||
|
||||
"""
|
||||
Defines types for Problem variables.
|
||||
|
||||
# Examples
|
||||
|
||||
The type of 'elements' is Vector{Element}
|
||||
|
||||
Add elements into the Problem element list.
|
||||
```@example
|
||||
a = [1, 2, 3]
|
||||
Problem.elements = a
|
||||
```
|
||||
|
||||
"""
|
||||
type Problem{P<:AbstractProblem}
|
||||
name :: AbstractString # descriptive name for problem
|
||||
name :: AbstractString # descriptive name for the problem
|
||||
dimension :: Int # degrees of freedom per node
|
||||
parent_field_name :: AbstractString # (optional) name of parent field e.g. "displacement"
|
||||
parent_field_name :: AbstractString # (optional) name of the parent field e.g. "displacement"
|
||||
elements :: Vector{Element}
|
||||
dofmap :: Dict{Element, Vector{Int64}} # connects element local dofs to global dofs
|
||||
dofmap :: Dict{Element, Vector{Int64}} # connects the element local dofs to the global dofs
|
||||
assembly :: Assembly
|
||||
fields :: Dict{AbstractString, Field}
|
||||
postprocess_fields :: Vector{String}
|
||||
properties :: P
|
||||
end
|
||||
|
||||
""" Construct a new field problem.
|
||||
"""
|
||||
Problem(problem_type, problem_name::String, problem_dimension)
|
||||
|
||||
Examples
|
||||
--------
|
||||
Create vector-valued (dim=3) elasticity problem:
|
||||
Construct a new field problem where `problem_type` is the type of the problem
|
||||
(Elasticity, Dirichlet, etc.), `problem_name` is the name of the problem and
|
||||
`problem_dimension` is the number of DOF:s in one node (2 in a 2D problem, 3
|
||||
in an elastic 3D problem, 6 in a 3D beam problem, etc.).
|
||||
|
||||
julia> prob1 = Problem(Elasticity, "this is my problem", 3)
|
||||
julia> prob2 = Problem(Elasticity, 3)
|
||||
# Examples
|
||||
|
||||
Create a vector-valued (dim=3) elasticity problem:
|
||||
|
||||
```@example
|
||||
prob1 = Problem(Elasticity, "this is my problem", 3)
|
||||
```
|
||||
|
||||
"""
|
||||
function Problem{P<:FieldProblem}(::Type{P}, name::AbstractString, dimension::Int64)
|
||||
return Problem{P}(name, dimension, "none", [], Dict(), Assembly(), Dict(), Vector(), P())
|
||||
end
|
||||
|
||||
""" Construct a new boundary problem.
|
||||
"""
|
||||
Construct a new boundary problem.
|
||||
|
||||
Examples
|
||||
--------
|
||||
Create Dirichlet boundary problem for vector-valued (dim=3) elasticity problem.
|
||||
Create a Dirichlet boundary problem for a vector-valued (dim=3) elasticity problem.
|
||||
|
||||
julia> bc1 = Problem(Dirichlet, "support", 3, "displacement")
|
||||
solver.
|
||||
@@ -150,7 +172,14 @@ function update!{P<:AbstractProblem}(problem::P, attr::Pair{String, String}...)
|
||||
end
|
||||
end
|
||||
|
||||
""" Initialize element ready for calculation. """
|
||||
"""
|
||||
function initialize!(problem_type, element_name, time)
|
||||
|
||||
Initialize the element ready for calculation, where `problem_type` is the type
|
||||
of the problem (Elasticity, Dirichlet, etc.), `element_name` is the name of a
|
||||
constructed element (see Element(element_type, connectivity_vector)) and `time`
|
||||
is the starting time of the initializing process.
|
||||
"""
|
||||
function initialize!(problem::Problem, element::Element, time::Float64)
|
||||
field_name = get_unknown_field_name(problem)
|
||||
field_dim = get_unknown_field_dimension(problem)
|
||||
@@ -165,7 +194,7 @@ function initialize!(problem::Problem, element::Element, time::Float64)
|
||||
end
|
||||
end
|
||||
|
||||
# if boundary problem, initialize field for main problem too
|
||||
# if a boundary problem, initialize also a field for the main problem
|
||||
is_boundary_problem(problem) || return
|
||||
field_name = get_parent_field_name(problem)
|
||||
if !haskey(element, field_name)
|
||||
@@ -183,7 +212,11 @@ function initialize!(problem::Problem, time::Float64=0.0)
|
||||
end
|
||||
end
|
||||
|
||||
""" Update problem solution vector for assembly. """
|
||||
"""
|
||||
update!(problem, assembly, u, la)
|
||||
|
||||
Update the problem solution vector for assembly.
|
||||
"""
|
||||
function update!(problem::Problem, assembly::Assembly, u::Vector, la::Vector)
|
||||
|
||||
# resize & fill with zeros vectors if length mismatch with current solution
|
||||
@@ -227,13 +260,16 @@ function update!(problem::Problem, assembly::Assembly, u::Vector, la::Vector)
|
||||
return assembly.u, assembly.la
|
||||
end
|
||||
|
||||
""" Return global solution (u, la) for problem.
|
||||
"""
|
||||
get_global_solution(problem, assembly)
|
||||
|
||||
Return a global solution (u, la) for a problem.
|
||||
|
||||
Notes
|
||||
-----
|
||||
If length of solution vector != number of nodes, i.e. field dimension is
|
||||
something other than 1, reshape vectors so it's length matches to the
|
||||
number of nodes so that one can easily get nodal results.
|
||||
If the length of solution vector != number of nodes, i.e. the field dimension is
|
||||
something else than 1, reshape vectors so that their length matches to the
|
||||
number of nodes. This helps to get nodal results easily.
|
||||
"""
|
||||
function get_global_solution(problem::Problem, assembly::Assembly)
|
||||
u = assembly.u
|
||||
@@ -251,7 +287,11 @@ function get_global_solution(problem::Problem, assembly::Assembly)
|
||||
end
|
||||
end
|
||||
|
||||
""" Update solution from assebly to elements. """
|
||||
"""
|
||||
update!(problem, assembly, elements, time)
|
||||
|
||||
Update a solution from the assebly to elements.
|
||||
"""
|
||||
function update!{P<:FieldProblem}(problem::Problem{P}, assembly::Assembly, elements::Vector{Element}, time::Float64)
|
||||
u, la = get_global_solution(problem, assembly)
|
||||
field_name = get_unknown_field_name(problem)
|
||||
|
||||
Reference in New Issue
Block a user