Bibletime – a bible study tool
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

317 lines
7.6 KiB

  1. /*********
  2. *
  3. * This file is part of BibleTime's source code, http://www.bibletime.info/.
  4. *
  5. * Copyright 1999-2006 by the BibleTime developers.
  6. * The BibleTime source code is licensed under the GNU General Public License version 2.0.
  7. *
  8. **********/
  9. #include "config.h"
  10. //BibleTime includes
  11. #include "cswordversekey.h"
  12. #include "cswordbiblemoduleinfo.h"
  13. #include "cswordcommentarymoduleinfo.h"
  14. //TQt includes
  15. #include <tqstringlist.h>
  16. //Sword includes
  17. #include <swmodule.h>
  18. #include <localemgr.h>
  19. // Boost includes
  20. // TODO: Detect Boost in autoconf
  21. #include <boost/scoped_ptr.hpp>
  22. CSwordVerseKey::CSwordVerseKey( CSwordModuleInfo* const module ) : CSwordKey(module) {
  23. if ( CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(module) ) {
  24. key( bible->lowerBound().key() );
  25. }
  26. }
  27. CSwordVerseKey::CSwordVerseKey( const CSwordVerseKey& k ) : CSwordKey(k), VerseKey(k) {}
  28. CSwordVerseKey::CSwordVerseKey( const VerseKey* const k, CSwordModuleInfo* const module ) : CSwordKey(module), VerseKey(*k) {}
  29. /** Clones this object. */
  30. CSwordKey* CSwordVerseKey::copy() const {
  31. return new CSwordVerseKey(*this);
  32. }
  33. /** Sets the module for this key */
  34. CSwordModuleInfo* const CSwordVerseKey::module( CSwordModuleInfo* const newModule ) {
  35. if (newModule && ((newModule->type() == CSwordModuleInfo::Bible) || (newModule->type() == CSwordModuleInfo::Commentary) ) ) {
  36. m_module = newModule;
  37. //check if the module contains the key we present
  38. CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(newModule);
  39. if (_compare(bible->lowerBound()) < 0) {
  40. key( bible->lowerBound() );
  41. }
  42. if (_compare(bible->upperBound()) > 0) {
  43. key( bible->upperBound() );
  44. }
  45. }
  46. return dynamic_cast<CSwordBibleModuleInfo*>(m_module);
  47. }
  48. /** Returns the current book as Text, not as integer. */
  49. const TQString CSwordVerseKey::book( const TQString& newBook ) {
  50. int min = 0;
  51. int max = 1;
  52. if (CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(module())) {
  53. const bool hasOT = bible->hasTestament(CSwordBibleModuleInfo::OldTestament);
  54. const bool hasNT = bible->hasTestament(CSwordBibleModuleInfo::NewTestament);
  55. if (hasOT && hasNT) {
  56. min = 0;
  57. max = 1;
  58. }
  59. else if (hasOT && !hasNT) {
  60. min = 0;
  61. max = 0;
  62. }
  63. else if (!hasOT && hasNT) {
  64. min = 1;
  65. max = 1;
  66. }
  67. else if (!hasOT && !hasNT) {
  68. min = 0;
  69. max = -1; //no loop
  70. }
  71. }
  72. if (!newBook.isEmpty()) {
  73. #ifdef SWORD_MULTIVERSE
  74. setBookName(newBook.utf8().data());
  75. #else
  76. bool finished = false;
  77. for (int testament = min; testament <= max && !finished; ++testament) {
  78. for (int book = 0; book < BMAX[testament] && !finished; ++book) {
  79. if ( !strcmp(newBook.utf8().data(), books[testament][book].name ) ) {
  80. Testament(testament+1);
  81. Book(book+1);
  82. finished = true;
  83. }
  84. }
  85. }
  86. #endif
  87. }
  88. if ( (Testament() >= min+1) && (Testament() <= max+1) && (Book() <= BMAX[min]) ) {
  89. return TQString::fromUtf8( getBookName() );
  90. }
  91. //return TQString::fromUtf8( books[min][0].name ); //return the first book, i.e. Genesis
  92. return TQString();
  93. }
  94. /** Sets the key we use to the parameter. */
  95. const TQString CSwordVerseKey::key() const {
  96. return TQString::fromUtf8(getText());
  97. }
  98. const char * CSwordVerseKey::rawKey() const {
  99. return getText();
  100. }
  101. const bool CSwordVerseKey::key( const TQString& newKey ) {
  102. return key( (const char*)newKey.utf8() );
  103. }
  104. const bool CSwordVerseKey::key( const char* newKey ) {
  105. if (newKey && (strlen(newKey)>0) ) {
  106. VerseKey::operator = (newKey);
  107. }
  108. else if (newKey && !strlen(newKey)) {
  109. CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(module());
  110. if ( bible ) {
  111. VerseKey::operator = ((const char*)bible->lowerBound().key().utf8());
  112. }
  113. }
  114. return !Error();
  115. }
  116. const bool CSwordVerseKey::next( const JumpType type ) {
  117. Error(); //clear Error status
  118. bool ret = true;
  119. switch (type) {
  120. case UseBook: {
  121. const int currentTestament = Testament();
  122. const int currentBook = Book();
  123. if ((currentTestament == 2) && (currentBook >= BMAX[currentTestament-1])) { //Revelation, i.e. end of navigation
  124. return false;
  125. }
  126. else if ((currentTestament == 1) && (currentBook >= BMAX[currentTestament-1])) { //Malachi, switch to the NT
  127. Testament(currentTestament+1);
  128. Book(1);
  129. }
  130. else {
  131. Book(Book()+1);
  132. }
  133. break;
  134. }
  135. case UseChapter: {
  136. Chapter(Chapter()+1);
  137. break;
  138. }
  139. case UseVerse: {
  140. if (m_module && m_module->module()) {
  141. const bool oldtqStatus = m_module->module()->getSkipConsecutiveLinks();
  142. m_module->module()->setSkipConsecutiveLinks(true);
  143. //disable headings for next verse
  144. const bool useHeaders = (Verse() == 0);
  145. const bool oldHeadingstqStatus = ((VerseKey*)(m_module->module()->getKey()))->Headings( useHeaders );
  146. //don't use setKey(), that would create a new key without Headings set
  147. m_module->module()->getKey()->setText( (const char*)key().utf8() );
  148. (*(m_module->module()) )++;
  149. ((VerseKey*)(m_module->module()->getKey()))->Headings(oldHeadingstqStatus);
  150. m_module->module()->setSkipConsecutiveLinks(oldtqStatus);
  151. if (!m_module->module()->Error()) {
  152. key( TQString::fromUtf8(m_module->module()->KeyText()) );
  153. }
  154. else {
  155. // Verse(Verse()+1);
  156. //don't change the key, restore the module's position
  157. m_module->module()->getKey()->setText( (const char*)key().utf8() );
  158. ret = false;
  159. break;
  160. }
  161. }
  162. else {
  163. Verse(Verse()+1);
  164. }
  165. break;
  166. }
  167. default:
  168. return false;
  169. }
  170. if ( CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(module()) ) {
  171. if (_compare(bible->lowerBound()) < 0 ) {
  172. key( bible->lowerBound() );
  173. ret = false;
  174. }
  175. if (_compare(bible->upperBound()) > 0 ) {
  176. key( bible->upperBound() );
  177. ret = false;
  178. }
  179. return ret;
  180. }
  181. else if (Error()) { //we have no module, so take care of VerseKey::Error()
  182. return false;
  183. }
  184. return ret;
  185. }
  186. const bool CSwordVerseKey::previous( const JumpType type ) {
  187. bool ret = true;
  188. switch (type) {
  189. case UseBook: {
  190. if ( (Book() == 1) && (Testament() == 1) ) { //Genesis
  191. return false;
  192. }
  193. else if ( (Book() == 1) && (Testament() == 2) ){ //Matthew
  194. Testament(1);
  195. Book(BMAX[0]);
  196. }
  197. else{
  198. Book( Book()-1 );
  199. }
  200. break;
  201. }
  202. case UseChapter: {
  203. Chapter(Chapter()-1);
  204. break;
  205. }
  206. case UseVerse: {
  207. if (m_module && m_module->module()) {
  208. const bool useHeaders = (Verse() == 0);
  209. const bool oldHeadingstqStatus = ((VerseKey*)(m_module->module()->getKey()))->Headings( useHeaders );
  210. m_module->module()->getKey()->setText( (const char*)key().utf8() );
  211. const bool oldtqStatus = m_module->module()->getSkipConsecutiveLinks();
  212. m_module->module()->setSkipConsecutiveLinks(true);
  213. ( *( m_module->module() ) )--;
  214. ((VerseKey*)(m_module->module()->getKey()))->Headings( oldHeadingstqStatus );
  215. m_module->module()->setSkipConsecutiveLinks(oldtqStatus);
  216. if (!m_module->module()->Error()) {
  217. key( TQString::fromUtf8(m_module->module()->KeyText()) );//don't use fromUtf8
  218. }
  219. else {
  220. ret = false;
  221. // Verse(Verse()-1);
  222. m_module->module()->getKey()->setText( (const char*)key().utf8() ); //restore module's key
  223. }
  224. }
  225. else {
  226. Verse(Verse()-1);
  227. }
  228. break;
  229. }
  230. default:
  231. return false;
  232. }
  233. if ( CSwordBibleModuleInfo* bible = dynamic_cast<CSwordBibleModuleInfo*>(module()) ) {
  234. if (_compare(bible->lowerBound()) < 0 ) {
  235. key( bible->lowerBound() );
  236. ret = false;
  237. }
  238. if (_compare(bible->upperBound()) > 0 ) {
  239. key( bible->upperBound() );
  240. ret = false;
  241. }
  242. return ret;
  243. }
  244. else if (Error()) {
  245. return false;
  246. }
  247. return ret;
  248. }
  249. /** Assignment operator for more ease of use. */
  250. CSwordVerseKey& CSwordVerseKey::operator = (const TQString& keyname) {
  251. key(keyname);
  252. return *this;
  253. }