9b5d99078e
[SVN r43422]
188 lines
6.6 KiB
XML
188 lines
6.6 KiB
XML
<?xml version="1.0" encoding="utf-8"?>
|
|
<!DOCTYPE library PUBLIC "-//Boost//DTD BoostBook XML V1.0//EN"
|
|
"../../../tools/boostbook/dtd/boostbook.dtd">
|
|
|
|
<!-- Copyright (c) 2001-2005 CrystalClear Software, Inc.
|
|
Subject to the Boost Software License, Version 1.0.
|
|
(See accompanying file LICENSE_1_0.txt or http://www.boost.org/LICENSE_1_0.txt)
|
|
-->
|
|
|
|
<section id="date_time.examples.meeting_planner">
|
|
<title>Teleconference Scheduler (partial listing)</title>
|
|
|
|
<para>
|
|
The Teleconference Scheduler is a Qt based example (found in the examples/qt directory). Partial listings of <link linkend="meeting_planner_hpp">meeting_planner.hpp</link> and <link linkend="planner_form_cpp">planner_form.cpp</link> are provided to illustrate techniques for using the local_date_time and tz_database objects.
|
|
</para>
|
|
|
|
<anchor id="planner_form_cpp" />
|
|
<para>
|
|
The planner_form class is derived from a QDialog. This listing illustrates the initialization of a tz_database object and using it to populate combo boxes with region lists. Only the init function is listed here for the sake of brevity.
|
|
</para>
|
|
<programlisting>
|
|
<![CDATA[
|
|
|
|
void planner_form::init() {
|
|
try{
|
|
tz_db.load_from_file("../../data/date_time_zonespec.csv");
|
|
}catch(boost::local_time::data_not_accessible dna) {
|
|
std::cerr << "Error with time zone data file: " << dna.what() << std::endl;
|
|
exit(EXIT_FAILURE);
|
|
}catch(boost::local_time::bad_field_count bfc) {
|
|
std::cerr << "Error with time zone data file: " << bfc.what() << std::endl;
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
|
|
// populate combo boxes with region names
|
|
typedef std::vector<std::string> vect;
|
|
vect regions = tz_db.region_list();
|
|
vect::const_iterator itr = regions.begin();
|
|
while(itr != regions.end()) {
|
|
comboBox1->insertItem(*itr);
|
|
comboBox2->insertItem(*itr);
|
|
comboBox3->insertItem(*itr);
|
|
++itr;
|
|
}
|
|
comboBox1->insertItem("<Select Region>", 0);
|
|
comboBox2->insertItem("<Select Region>", 0);
|
|
comboBox3->insertItem("<Select Region>", 0);
|
|
|
|
// set up dateEdit
|
|
dateEdit2->setSeparator("-");
|
|
|
|
this->reset();
|
|
}
|
|
|
|
]]>
|
|
</programlisting>
|
|
|
|
<anchor id="meeting_planner_hpp" />
|
|
<para>
|
|
This class coordinates local times across multiple time zones. It accomplishes this by iterating across a collection of time zones and verifying that the target time falls within a set period (a workday).
|
|
</para>
|
|
<programlisting>
|
|
<![CDATA[
|
|
|
|
/* The heart of the meeting_planner is the synchronization of different
|
|
* time zones to a single point in time.
|
|
* The class takes a vector of regions and a date. The default time
|
|
* range is 9am to 5pm but can be changed.
|
|
* The resulting time specs are returned as a vector of strings
|
|
*/
|
|
|
|
|
|
#include "boost/date_time/gregorian/gregorian.hpp"
|
|
#include "boost/date_time/posix_time/posix_time.hpp"
|
|
#include "boost/date_time/local_time/local_time.hpp"
|
|
#include "boost/shared_ptr.hpp"
|
|
#include <string>
|
|
#include <vector>
|
|
#include <locale>
|
|
|
|
using namespace boost;
|
|
using namespace local_time;
|
|
using namespace posix_time;
|
|
|
|
//! Coordinates meeting times accounting for time zone differences
|
|
class meeting_planner {
|
|
public:
|
|
typedef std::vector<shared_ptr<time_zone_base> > vector_type;
|
|
// a multimap is used so time_zones can be sorted according to utc_offset
|
|
typedef std::multimap<posix_time::time_duration, shared_ptr<time_zone_base> > zone_map_type;
|
|
typedef std::vector<std::string> result_type;
|
|
|
|
meeting_planner(const gregorian::date& d, const vector_type& v)
|
|
: l_time(posix_time::not_a_date_time, shared_ptr<time_zone_base>()),
|
|
workday(ptime(d,hours(9)), time_duration(8,0,0,1))
|
|
{
|
|
vector_type::const_iterator iter = v.begin();
|
|
while(iter != v.end()) {
|
|
time_duration offset(0,0,0);
|
|
if(*iter == NULL) {
|
|
offset = hours(0);
|
|
}
|
|
else{
|
|
// null pointers may wind up in the vector
|
|
// TODO: this should be fixed in tz_database
|
|
offset = (*iter)->base_utc_offset();
|
|
}
|
|
zones.insert(zone_map_type::value_type(offset, *iter));
|
|
++iter;
|
|
}
|
|
|
|
// set l_time to noon UTC
|
|
l_time = local_date_time(posix_time::ptime(d, posix_time::hours(12)),
|
|
shared_ptr<time_zone_base>());
|
|
}
|
|
|
|
//! Changes range of valid meeting times (ie. The hours in a workday) times are inclusive
|
|
void change_range(const time_duration& start, const time_duration& end)
|
|
{
|
|
ptime pt(l_time.date(), start);
|
|
// add one unit to make the give times inclusive
|
|
workday = time_period(pt, (end - start) + time_duration::unit());
|
|
}
|
|
|
|
//! strings returned in the form of "yyyy-Mon-dd: hh:mm Zzz [repeat]"
|
|
result_type coordinate_time() const
|
|
{
|
|
using namespace posix_time;
|
|
|
|
result_type result;
|
|
bool flag = true;
|
|
std::stringstream ss;
|
|
ss.str("");
|
|
|
|
// set the output format for local_date_time to only give
|
|
// time_of_day & zone offset
|
|
typedef boost::date_time::time_facet<local_date_time, char> ldt_facet;
|
|
ldt_facet* timefacet = new ldt_facet("%H:%M (%q)");
|
|
std::locale loc(std::locale::classic(), timefacet);
|
|
ss.imbue(loc);
|
|
|
|
// backup a full day and start iterating from there
|
|
// I went overkill because I've got no decent
|
|
// algorithm to set a starting point (yet)
|
|
local_date_time tmp = l_time - gregorian::days(1);
|
|
zone_map_type::const_iterator iter;
|
|
for(int i = 0; i < 48; ++i) {
|
|
iter = zones.begin();
|
|
flag = true;
|
|
tmp += posix_time::hours(1);
|
|
|
|
while(iter != zones.end() && flag) {
|
|
if(!workday.contains(tmp.local_time_in(iter->second).local_time())) {
|
|
flag = false;
|
|
}
|
|
++iter;
|
|
}
|
|
|
|
if(flag) {
|
|
iter = zones.begin();
|
|
ss << tmp.date() << ':';
|
|
while(iter != zones.end()) {
|
|
ss << ' ' << tmp.local_time_in(iter->second);
|
|
++iter;
|
|
if(iter != zones.end()) {
|
|
ss << ',';
|
|
}
|
|
}
|
|
result.push_back(ss.str());
|
|
ss.str("");
|
|
}
|
|
}
|
|
if(result.empty()) {
|
|
result.push_back("Scheduling within the time period given is not possible for these time zones.");
|
|
}
|
|
return result;
|
|
}
|
|
|
|
private:
|
|
zone_map_type zones;
|
|
local_date_time l_time;
|
|
time_period workday;
|
|
};
|
|
|
|
]]>
|
|
</programlisting>
|
|
</section>
|