Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/Actions/FillAction/SuspendInMoleculeAction.cpp

    r2440ce raa55d0  
    129129  filler->CenterEdge();
    130130
     131  /// first we need to calculate some volumes and masses
    131132  std::vector<molecule *> molecules = World::getInstance().getAllMolecules();
    132   if (molecules.size() < 2) {
    133     STATUS("There must be at least two molecules: filler and to be suspended.");
    134     return Action::failure;
    135   }
    136 
    137   /// first we need to calculate some volumes and masses
    138133  double totalmass = 0.;
    139134  const bool IsAngstroem = true;
     
    144139      iter != molecules.end(); ++iter)
    145140  {
    146     // skip the filler
    147     if (*iter == filler)
    148       continue;
    149141    molecule & mol = **iter;
    150142    const double mass = calculateMass(mol);
     
    160152  LOG(1, "INFO: The average density is " << setprecision(10)
    161153      << totalmass / clustervolume << " atomicmassunit/"
    162       << (IsAngstroem ? " angstrom" : " atomiclength") << "^3.");
    163   if ( ((totalmass / clustervolume < 1.) && (params.density.get() > 1.))
    164       || ((totalmass / clustervolume > 1.) && (params.density.get() < 1.))) {
    165     STATUS("Desired and present molecular densities must both be either in [0,1) or in (1, inf).");
    166     return Action::failure;
    167   }
     154      << (IsAngstroem ? "angstrom" : "atomiclength") << "^3.");
    168155
    169156  // calculate maximum solvent density
    170157  std::vector<double> fillerdiameters(NDIM, 0.);
    171   const double fillervolume = calculateEnvelopeVolume(*filler, fillerdiameters);
    172   const double fillermass = calculateMass(*filler);
    173   LOG(1, "INFO: The filler's mass is " << setprecision(10)
    174       << fillermass << " atomicmassunit, and it's volume is "
    175       << fillervolume << (IsAngstroem ? " angstrom" : " atomiclength") << "^3.");
    176   const double solventdensity = fillermass / fillervolume;
     158  const double solventdensity =
     159      calculateMass(*filler) / calculateEnvelopeVolume(*filler, fillerdiameters);
     160
     161  std::vector<unsigned int> counts(3, 0);
     162  Vector offset(.5,.5,.5);
    177163
    178164  /// solve cubic polynomial
    179165  double cellvolume = 0.;
    180166  LOG(1, "Solving equidistant suspension in water problem ...");
    181   // s = solvent, f = filler, 0 = initial molecules/cluster
    182   // v_s = v_0 + v_f, m_s = m_0 + rho_f * v_f --> rho_s = m_s/v_s ==> v_f = (m_0 - rho_s * v_o) / (rho_s - rho_f)
    183   cellvolume = (totalmass - params.density.get() * clustervolume) / (params.density.get() - 1.) + clustervolume;
     167  cellvolume = (totalmass / solventdensity
     168      - (totalmass / clustervolume)) / (params.density.get() - 1.);
    184169  LOG(1, "Cellvolume needed for a density of " << params.density.get()
    185170      << " g/cm^3 is " << cellvolume << " angstroem^3.");
     
    188173      (GreatestDiameter[0] * GreatestDiameter[1] * GreatestDiameter[2]);
    189174  LOG(1, "Minimum volume of the convex envelope contained in a rectangular box is "
    190       << minimumvolume << " angstrom^3.");
     175      << minimumvolume << "angstrom^3.");
    191176
    192177  if (minimumvolume > cellvolume) {
     
    202187        + GreatestDiameter[1] * GreatestDiameter[2];
    203188    BoxLengths[2] = minimumvolume - cellvolume;
    204     std::vector<double> x(3, 0.);
     189    double x0 = 0.;
     190    double x1 = 0.;
     191    double x2 = 0.;
    205192    // for cubic polynomial there are either 1 or 3 unique solutions
    206     if (gsl_poly_solve_cubic(BoxLengths[0], BoxLengths[1], BoxLengths[2], &x[0], &x[1], &x[2]) == 1) {
    207       x[1] = x[0];
    208       x[2] = x[0];
    209     } else {
    210       std::swap(x[0], x[2]); // sorted in ascending order
    211     }
    212     LOG(0, "RESULT: The resulting spacing is: " << x << " .");
     193    if (gsl_poly_solve_cubic(BoxLengths[0], BoxLengths[1], BoxLengths[2], &x0, &x1, &x2) == 1)
     194      LOG(0, "RESULT: The resulting spacing is: " << x0 << " .");
     195    else {
     196      LOG(0, "RESULT: The resulting spacings are: " << x0 << " and " << x1 << " and " << x2 << " .");
     197      std::swap(x0, x2); // sorted in ascending order
     198    }
    213199
    214200    cellvolume = 1.;
    215201    for (size_t i = 0; i < NDIM; ++i) {
    216       BoxLengths[i] = x[i] + GreatestDiameter[i];
     202      BoxLengths[i] = x0 + GreatestDiameter[i];
    217203      cellvolume *= BoxLengths[i];
    218204    }
    219   }
    220 
    221   // TODO: Determine counts from resulting mass correctly (hard problem due to integers)
    222   std::vector<unsigned int> counts(3, 0);
    223   const unsigned int totalcounts = round(params.density.get() * cellvolume - totalmass) / fillermass;
    224   if (totalcounts > 0) {
    225     counts[0] = ceil(BoxLengths[0]/3.1);
    226     counts[1] = ceil(BoxLengths[1]/3.1);
    227     counts[2] = ceil(BoxLengths[2]/3.1);
     205
     206    // set new box dimensions
     207    LOG(0, "Translating to box with these boundaries.");
     208    {
     209      RealSpaceMatrix domain;
     210      for(size_t i =0; i<NDIM;++i)
     211        domain.at(i,i) = BoxLengths[i];
     212      World::getInstance().setDomain(domain);
     213    }
     214//    mol->CenterInBox();
    228215  }
    229216
     
    244231      params.RandMoleculeDisplacement.get(),
    245232      params.DoRotate.get());
    246   Vector offset(.5,.5,.5);
    247233  filler_preparator.addCubeMesh(
    248234      counts,
Note: See TracChangeset for help on using the changeset viewer.