File:  [Public] / libwww / Library / src / HTHist.c
Revision 2.2: download - view: text, annotated - select for diffs
Fri May 19 02:05:18 1995 UTC (29 years ago) by frystyk
Branches: MAIN
CVS tags: v3/1pre3, v3/1pre2, v3/1pre1, v3/1, WinNT, NT1, NT, NNTP, HEAD
final swap to MIT statements

/*								    HTHist.c
**	NAVIGATION MANAGER
**
**	(c) COPYRIGHT MIT 1995.
**	Please first read the full copyright statement in the file COPYRIGH.
*/

/* Library include files */
#include "tcp.h"
#include "HTUtils.h"
#include "HTHist.h"

static HTList * history;	/* List of visited anchors */


/*		Record the jump to an anchor
**		----------------------------
*/

void HTHistory_record
  ARGS1 (HTAnchor *,destination)
{
  if (destination) {
    if (! history)
      history = HTList_new();
    HTList_addObject (history, destination);
  }
}

/*		Go back in history (find the last visited node)
**		------------------
*/

BOOL HTHistory_canBacktrack
  NOARGS
{
  return (HTList_objectAt (history, 1) != NULL);
}

HTAnchor * HTHistory_backtrack
  NOARGS  /* FIXME: Should we add a `sticky' option ? */
{
  if (HTHistory_canBacktrack())
    HTList_removeLastObject (history);
  /* is Home if can't backtrack */
  return (HTAnchor *) HTList_lastObject (history);
}


PUBLIC HTAnchor * HTHistory_back ARGS1 (HTAnchor *,cur_anch)
{
    if (HTHistory_canBacktrack()) {
	int pos = HTList_indexOf(history, cur_anch);
	return ((HTAnchor *) HTList_objectAt(history, pos + 1));
    }
    return NULL;               /* to indicate that browser should not redraw */
}


PUBLIC HTAnchor * HTHistory_forward ARGS1 (HTAnchor *,cur_anch)
{
    int pos = HTList_indexOf(history, cur_anch);
    if (pos <= 0)
	return NULL;
    else
	return ((HTAnchor *) HTList_objectAt(history, pos - 1));
}

/*

PUBLIC HTAnchor * HTHistory_delete ARGS1 (HTAnchor *,cur_anch)
{
    int pos = HTList_indexOf(history, cur_anch);
    if (pos <= 0)
	return NULL;
    else
	return ((HTAnchor *) HTList_objectAt(history, pos - 1));
}

*/


/*		Browse through references in the same parent node
**		-------------------------------------------------
**
**	Take the n-th child's link after or before the one we took to get here.
**	Positive offset means go towards most recently added children.
*/

HTAnchor * HTHistory_moveBy ARGS1 (int,offset)
{
  HTAnchor * last = (HTAnchor *) HTList_objectAt (history, 1);
  if (! last)
    return NULL;  /* No last visited node */
  if (last != (HTAnchor *) last->parent) {  /* Was a child */
    HTList * kids = last->parent->children;
    int i = HTList_indexOf (kids, last); 
    HTAnchor * nextOne = (HTAnchor *) HTList_objectAt (kids, i - offset);
    if (nextOne) {
      HTAnchor * destination = HTAnchor_followMainLink (nextOne);
      if (destination) {
	HTList_removeLastObject (history);
	HTList_removeLastObject (history);
	HTList_addObject (history, nextOne);
	HTList_addObject (history, destination);
      }
      return destination;
    } else {
      if (TRACE) fprintf(TDEST, 
      		"HTHistory_moveBy: offset by %+d goes out of list %p.\n",
		offset, (void*)kids);
      return NULL;
    }
  } else {  /* Was a parent */
    return NULL;  /* FIXME we could possibly follow the next link... */
  }
}

BOOL HTHistory_canMoveBy
 ARGS1 (int,offset)
{
  HTAnchor * last = (HTAnchor *) HTList_objectAt (history, 1);
  if (! last)
    return NO;  /* No last visited node */
  if (last != (HTAnchor *) last->parent) {  /* Was a child */
    HTList * kids = last->parent->children;
    int i = HTList_indexOf (kids, last); 
    return (HTList_objectAt (kids, i - offset) != NULL);
  } else {  /* Was a parent */
    return NO;  /* FIXME we could possibly follow the next link... */
  }
}


/*				Retrieval
**				=========
*/

/*		Read numbered visited anchor (1 is the oldest)
**		----------------------------
*/

HTAnchor * HTHistory_read ARGS1 (int, number)
{
    return (HTAnchor *) (HTList_objectAt(history,
					 HTList_count(history)-number));
}


/*		Recall numbered visited anchor (1 is the oldest)
**		------------------------------
**	This reads the anchor and stores it again in the list, except if last.
*/

HTAnchor * HTHistory_recall ARGS1 (int,number)
{
    HTAnchor * destination = (HTAnchor *)
	HTList_objectAt (history, HTList_count (history) - number);
    if (destination && destination != HTList_lastObject (history))
	HTList_addObject (history, destination);
    return destination;
}

/*		Number of Anchors stored
**		------------------------
**
**	This is needed in order to check the validity of certain commands
**	for menus, etc.
(not needed for now. Use canBacktrack, etc.)
int HTHistory_count
  NOARGS
{
  return HTList_count (history);
}
*/

/*		Change last history entry
**		-------------------------
**
**	Sometimes we load a node by one anchor but leave by a different
**	one, and it is the one we left from which we want to remember.
*/

void HTHistory_leavingFrom
  ARGS1 (HTAnchor *,anchor)
{
  if (HTList_removeLastObject (history))
    HTList_addObject (history, anchor);
  else
    if (TRACE) fprintf(TDEST, "HTHistory_leavingFrom: empty history !\n");
}

Webmaster