diff miscellany/less-177/brac.c @ 0:bce86c4163a3

Initial revision
author kono
date Mon, 18 Apr 2005 23:46:02 +0900
parents
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/miscellany/less-177/brac.c	Mon Apr 18 23:46:02 2005 +0900
@@ -0,0 +1,90 @@
+/*
+ * Routines to perform bracket matching functions.
+ */
+
+#include "less.h"
+#include "position.h"
+
+/*
+ * Try to match the n-th open bracket 
+ *  which appears in the top displayed line (forwdir),
+ * or the n-th close bracket 
+ *  which appears in the bottom displayed line (!forwdir).
+ * The characters which serve as "open bracket" and 
+ * "close bracket" are given.
+ */
+	public void
+match_brac(obrac, cbrac, forwdir, n)
+	register int obrac;
+	register int cbrac;
+	int forwdir;
+	int n;
+{
+	register int c;
+	register int nest;
+	POSITION pos;
+	int (*chget)();
+
+	extern int ch_forw_get(), ch_back_get();
+
+	/*
+	 * Seek to the line containing the open bracket.
+	 * This is either the top or bottom line on the screen,
+	 * depending on the type of bracket.
+	 */
+	pos = position((forwdir) ? TOP : BOTTOM);
+	if (pos == NULL_POSITION || ch_seek(pos))
+	{
+		if (forwdir)
+			error("Nothing in top line", NULL_PARG);
+		else
+			error("Nothing in bottom line", NULL_PARG);
+		return;
+	}
+
+	/*
+	 * Look thru the line to find the open bracket to match.
+	 */
+	do
+	{
+		if ((c = ch_forw_get()) == '\n' || c == EOI)
+		{
+			if (forwdir)
+				error("No bracket in top line", NULL_PARG);
+			else
+				error("No bracket in bottom line", NULL_PARG);
+			return;
+		}
+	} while (c != obrac || --n > 0);
+
+	/*
+	 * Position the file just "after" the open bracket
+	 * (in the direction in which we will be searching).
+	 * If searching forward, we are already after the bracket.
+	 * If searching backward, skip back over the open bracket.
+	 */
+	if (!forwdir)
+		(void) ch_back_get();
+
+	/*
+	 * Search the file for the matching bracket.
+	 */
+	chget = (forwdir) ? ch_forw_get : ch_back_get;
+	nest = 0;
+	while ((c = (*chget)()) != EOI)
+	{
+		if (c == obrac)
+			nest++;
+		else if (c == cbrac && --nest < 0)
+		{
+			/*
+			 * Found the matching bracket.
+			 * If searching backward, put it on the top line.
+			 * If searching forward, put it on the bottom line.
+			 */
+			jump_line_loc(ch_tell(), forwdir ? -1 : 1);
+			return;
+		}
+	}
+	error("No matching bracket", NULL_PARG);
+}