Annotation of libwww/Library/src/HTHist.c, revision 2.1
2.1 ! frystyk 1: /* HTHist.c
! 2: ** NAVIGATION MANAGER
! 3: **
! 4: ** (c) COPYRIGHT CERN 1994.
! 5: ** Please first read the full copyright statement in the file COPYRIGH.
! 6: */
! 7:
! 8: /* Library include files */
! 9: #include "tcp.h"
! 10: #include "HTUtils.h"
! 11: #include "HTHist.h"
! 12:
! 13: static HTList * history; /* List of visited anchors */
! 14:
! 15:
! 16: /* Record the jump to an anchor
! 17: ** ----------------------------
! 18: */
! 19:
! 20: void HTHistory_record
! 21: ARGS1 (HTAnchor *,destination)
! 22: {
! 23: if (destination) {
! 24: if (! history)
! 25: history = HTList_new();
! 26: HTList_addObject (history, destination);
! 27: }
! 28: }
! 29:
! 30: /* Go back in history (find the last visited node)
! 31: ** ------------------
! 32: */
! 33:
! 34: BOOL HTHistory_canBacktrack
! 35: NOARGS
! 36: {
! 37: return (HTList_objectAt (history, 1) != NULL);
! 38: }
! 39:
! 40: HTAnchor * HTHistory_backtrack
! 41: NOARGS /* FIXME: Should we add a `sticky' option ? */
! 42: {
! 43: if (HTHistory_canBacktrack())
! 44: HTList_removeLastObject (history);
! 45: /* is Home if can't backtrack */
! 46: return (HTAnchor *) HTList_lastObject (history);
! 47: }
! 48:
! 49:
! 50: PUBLIC HTAnchor * HTHistory_back ARGS1 (HTAnchor *,cur_anch)
! 51: {
! 52: if (HTHistory_canBacktrack()) {
! 53: int pos = HTList_indexOf(history, cur_anch);
! 54: return ((HTAnchor *) HTList_objectAt(history, pos + 1));
! 55: }
! 56: return NULL; /* to indicate that browser should not redraw */
! 57: }
! 58:
! 59:
! 60: PUBLIC HTAnchor * HTHistory_forward ARGS1 (HTAnchor *,cur_anch)
! 61: {
! 62: int pos = HTList_indexOf(history, cur_anch);
! 63: if (pos <= 0)
! 64: return NULL;
! 65: else
! 66: return ((HTAnchor *) HTList_objectAt(history, pos - 1));
! 67: }
! 68:
! 69: /*
! 70:
! 71: PUBLIC HTAnchor * HTHistory_delete ARGS1 (HTAnchor *,cur_anch)
! 72: {
! 73: int pos = HTList_indexOf(history, cur_anch);
! 74: if (pos <= 0)
! 75: return NULL;
! 76: else
! 77: return ((HTAnchor *) HTList_objectAt(history, pos - 1));
! 78: }
! 79:
! 80: */
! 81:
! 82:
! 83: /* Browse through references in the same parent node
! 84: ** -------------------------------------------------
! 85: **
! 86: ** Take the n-th child's link after or before the one we took to get here.
! 87: ** Positive offset means go towards most recently added children.
! 88: */
! 89:
! 90: HTAnchor * HTHistory_moveBy ARGS1 (int,offset)
! 91: {
! 92: HTAnchor * last = (HTAnchor *) HTList_objectAt (history, 1);
! 93: if (! last)
! 94: return NULL; /* No last visited node */
! 95: if (last != (HTAnchor *) last->parent) { /* Was a child */
! 96: HTList * kids = last->parent->children;
! 97: int i = HTList_indexOf (kids, last);
! 98: HTAnchor * nextOne = (HTAnchor *) HTList_objectAt (kids, i - offset);
! 99: if (nextOne) {
! 100: HTAnchor * destination = HTAnchor_followMainLink (nextOne);
! 101: if (destination) {
! 102: HTList_removeLastObject (history);
! 103: HTList_removeLastObject (history);
! 104: HTList_addObject (history, nextOne);
! 105: HTList_addObject (history, destination);
! 106: }
! 107: return destination;
! 108: } else {
! 109: if (TRACE) fprintf(TDEST,
! 110: "HTHistory_moveBy: offset by %+d goes out of list %p.\n",
! 111: offset, (void*)kids);
! 112: return NULL;
! 113: }
! 114: } else { /* Was a parent */
! 115: return NULL; /* FIXME we could possibly follow the next link... */
! 116: }
! 117: }
! 118:
! 119: BOOL HTHistory_canMoveBy
! 120: ARGS1 (int,offset)
! 121: {
! 122: HTAnchor * last = (HTAnchor *) HTList_objectAt (history, 1);
! 123: if (! last)
! 124: return NO; /* No last visited node */
! 125: if (last != (HTAnchor *) last->parent) { /* Was a child */
! 126: HTList * kids = last->parent->children;
! 127: int i = HTList_indexOf (kids, last);
! 128: return (HTList_objectAt (kids, i - offset) != NULL);
! 129: } else { /* Was a parent */
! 130: return NO; /* FIXME we could possibly follow the next link... */
! 131: }
! 132: }
! 133:
! 134:
! 135: /* Retrieval
! 136: ** =========
! 137: */
! 138:
! 139: /* Read numbered visited anchor (1 is the oldest)
! 140: ** ----------------------------
! 141: */
! 142:
! 143: HTAnchor * HTHistory_read ARGS1 (int, number)
! 144: {
! 145: return (HTAnchor *) (HTList_objectAt(history,
! 146: HTList_count(history)-number));
! 147: }
! 148:
! 149:
! 150: /* Recall numbered visited anchor (1 is the oldest)
! 151: ** ------------------------------
! 152: ** This reads the anchor and stores it again in the list, except if last.
! 153: */
! 154:
! 155: HTAnchor * HTHistory_recall ARGS1 (int,number)
! 156: {
! 157: HTAnchor * destination = (HTAnchor *)
! 158: HTList_objectAt (history, HTList_count (history) - number);
! 159: if (destination && destination != HTList_lastObject (history))
! 160: HTList_addObject (history, destination);
! 161: return destination;
! 162: }
! 163:
! 164: /* Number of Anchors stored
! 165: ** ------------------------
! 166: **
! 167: ** This is needed in order to check the validity of certain commands
! 168: ** for menus, etc.
! 169: (not needed for now. Use canBacktrack, etc.)
! 170: int HTHistory_count
! 171: NOARGS
! 172: {
! 173: return HTList_count (history);
! 174: }
! 175: */
! 176:
! 177: /* Change last history entry
! 178: ** -------------------------
! 179: **
! 180: ** Sometimes we load a node by one anchor but leave by a different
! 181: ** one, and it is the one we left from which we want to remember.
! 182: */
! 183:
! 184: void HTHistory_leavingFrom
! 185: ARGS1 (HTAnchor *,anchor)
! 186: {
! 187: if (HTList_removeLastObject (history))
! 188: HTList_addObject (history, anchor);
! 189: else
! 190: if (TRACE) fprintf(TDEST, "HTHistory_leavingFrom: empty history !\n");
! 191: }
Webmaster