commit 7e599a16abfc8e5e3cd9438fe047beea7b3986f9
parent 7220628689e620bc37407d2f294014c2cb378c56
Author: Remy Noulin <loader2x@gmail.com>
Date: Sat, 19 May 2018 23:40:24 +0200
clispinner sheepy package
clispinner.c | 208 +++++++++++++++++++++++++++++++++++++++++++++++++++
clispinner.h | 106 ++++++++++++++++++++++++++
clispinnerInternal.h | 3 +
package.yml | 18 +++++
test.c | 55 ++++++++++++++
5 files changed, 390 insertions(+)
Diffstat:
| A | clispinner.c | | | 208 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
| A | clispinner.h | | | 106 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
| A | clispinnerInternal.h | | | 3 | +++ |
| A | package.yml | | | 18 | ++++++++++++++++++ |
| A | test.c | | | 55 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
5 files changed, 390 insertions(+), 0 deletions(-)
diff --git a/clispinner.c b/clispinner.c
@@ -0,0 +1,208 @@
+
+#include "libsheepyObject.h"
+#include "clispinner.h"
+#include "clispinnerInternal.h"
+
+
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+
+void initiateClispinner(clispinnert *self);
+void registerMethodsClispinner(clispinnerFunctionst *f);
+void initiateAllocateClispinner(clispinnert **self);
+void finalizeClispinner(void);
+clispinnert* allocClispinner(u64 interval, const char *title);
+internal void freeClispinner(clispinnert *self);
+internal void terminateClispinner(clispinnert **self);
+internal char* toStringClispinner(clispinnert *self);
+internal clispinnert* duplicateClispinner(clispinnert *self);
+internal void smashClispinner(clispinnert **self);
+internal void finishClispinner(clispinnert **self);
+internal void startClispinner(clispinnert *self);
+internal void stopClispinner(clispinnert *self);
+internal void createTheSignalTimerClispinner(clispinnert *self);
+internal void setSignalTimerClispinner(clispinnert *self, signalTimert * signalTimer);
+internal signalTimert* getSignalTimerClispinner(clispinnert *self);
+internal void pauseProcessClispinner(clispinnert *self);
+internal void setSpinStringClispinner(clispinnert *self, const char *spinString);
+internal void setIntervalClispinner(clispinnert *self, u64 interval);
+internal bool isSpinningClispinner(clispinnert *self);
+
+static signalTimert *theSignalTimerAddr = NULL;
+static bool cliSpinnerAllocatedTheSignalTimer = false;
+
+internal void doSpin(void *arg);
+
+void initiateClispinner(clispinnert *self) {
+
+ self->type = "clispinner";
+ if (!clispinnerF) {
+ clispinnerF = malloc(sizeof(clispinnerFunctionst));
+ registerMethodsClispinner(clispinnerF);
+ pErrorNot0(atexit(finalizeClispinner));
+ }
+ self->f = clispinnerF;
+ self->isSpinning = false;
+ self->interval = 100;
+ self->title[0] = 0;
+ strcpy(self->spinString, "|/-\\");
+}
+
+void registerMethodsClispinner(clispinnerFunctionst *f) {
+
+ f->free = freeClispinner;
+ f->terminate = terminateClispinner;
+ f->toString = toStringClispinner;
+ f->duplicate = duplicateClispinner;
+ f->smash = smashClispinner;
+ f->finish = finishClispinner;
+ f->start = startClispinner;
+ f->stop = stopClispinner;
+ f->createTheSignalTimer = createTheSignalTimerClispinner;
+ f->setSignalTimer = setSignalTimerClispinner;
+ f->getSignalTimer = getSignalTimerClispinner;
+ f->pauseProcess = pauseProcessClispinner;
+ f->setSpinString = setSpinStringClispinner;
+ f->setInterval = setIntervalClispinner;
+ f->isSpinning = isSpinningClispinner;
+}
+
+void initiateAllocateClispinner(clispinnert **self) {
+
+ if (self) {
+ (*self) = malloc(sizeof(clispinnert));
+ if (*self) {
+ initiateClispinner(*self);
+ }
+ }
+}
+
+void finalizeClispinner(void) {
+
+ if (clispinnerF) {
+ free(clispinnerF);
+ clispinnerF = NULL;
+ }
+}
+
+clispinnert* allocClispinner(u64 interval, const char *title) {
+ clispinnert *r = NULL;
+
+ initiateAllocateClispinner(&r);
+ createTheSignalTimerClispinner(r);
+ r->interval = interval;
+
+ if (title) {
+ strLCpy(r->title, CLISPINNERTITLESIZE, title);
+ }
+ else r->title[0] = 0;
+ return(r);
+}
+
+
+internal void freeClispinner(clispinnert *self) {
+
+ /* no internal data to free */
+ return;
+}
+
+internal void terminateClispinner(clispinnert **self) {
+
+ // stop and terminate theSignalTimerAddr if clispinner allocated it
+ if (theSignalTimerAddr and cliSpinnerAllocatedTheSignalTimer) {
+ terminateG(theSignalTimerAddr);
+ cliSpinnerAllocatedTheSignalTimer = false;
+ }
+
+ freeClispinner(*self);
+ free(*self);
+ *self = NULL;
+}
+
+
+internal char* toStringClispinner(clispinnert *self) {
+
+ return(strdup("TODO - class template"));
+}
+
+internal clispinnert* duplicateClispinner(clispinnert *self) {
+
+ createAllocateClispinner(dup);
+ /* TODO COPY data */
+ return(dup);
+}
+
+internal void smashClispinner(clispinnert **self) {
+
+ finishClispinner(self);
+}
+
+internal void finishClispinner(clispinnert **self) {
+
+ free(*self);
+ *self = NULL;
+}
+
+
+internal void startClispinner(clispinnert *self) {
+
+ if (!theSignalTimerAddr) return;
+
+ indexerInit(self->ix, strlen(self->spinString));
+ startTimerG(theSignalTimerAddr, self->interval, doSpin, self);
+
+ printf(self->title);
+ self->isSpinning = true;
+ // set unbuffered stdout, to show the characters directly
+ //setbuf(stdout, NULL);
+}
+
+internal void stopClispinner(clispinnert *self) {
+ if (!theSignalTimerAddr) return;
+ stopG(theSignalTimerAddr);
+ self->isSpinning = false;
+}
+
+internal void createTheSignalTimerClispinner(clispinnert *self) {
+ initiateAllocateSignalTimer(&theSignalTimerAddr);
+ cliSpinnerAllocatedTheSignalTimer = true;
+}
+
+internal void setSignalTimerClispinner(clispinnert *self, signalTimert * signalTimer) {
+ theSignalTimerAddr = signalTimer;
+}
+
+internal signalTimert* getSignalTimerClispinner(clispinnert *self) {
+ return theSignalTimerAddr;
+}
+
+internal void pauseProcessClispinner(clispinnert *self) {
+ if (!theSignalTimerAddr) return;
+ pauseProcessG(theSignalTimerAddr);
+}
+
+internal void setSpinStringClispinner(clispinnert *self, const char *spinString) {
+ if (spinString) {
+ strLCpy(self->spinString, 32, spinString);
+ }
+}
+
+internal void setIntervalClispinner(clispinnert *self, u64 interval) {
+ self->interval = interval;
+ if (!theSignalTimerAddr) return;
+ setIntervalG(theSignalTimerAddr, interval);
+}
+
+internal bool isSpinningClispinner(clispinnert *self) {
+ return self->isSpinning;
+}
+
+internal void doSpin(void *arg) {
+ cast(clispinnert *, this, arg);
+
+ indexerPush(this->ix);
+ putchar(this->spinString[this->ix.last]);
+ fflush(stdout);
+ putchar('\b');
+}
diff --git a/clispinner.h b/clispinner.h
@@ -0,0 +1,106 @@
+#pragma once
+
+#include "shpPackages/signalTimer/signalTimer.h"
+
+#define startG(obj) (obj)->f->start(obj)
+#define createTheSignalTimerG(obj) (obj)->f->createTheSignalTimer(obj)
+#define setSignalTimerG(obj, signalTimer) (obj)->f->setSignalTimer(obj, signalTimer)
+//pauseProcessG
+#define setSpinStringG(obj, spinString) (obj)->f->setSpinString(obj, spinString)
+//setInterval
+#define isSpinningG(obj) (obj)->f->isSpinning(obj)
+
+/* Class clispinner */
+typedef struct clispinner clispinnert;
+
+/* for object inheriting clispinner, cast to clispinner to be able to use this class functions and generics*/
+#define cClispinner(self) ( (clispinnert*) self )
+
+typedef void (*freeClispinnerFt) (clispinnert *self);
+typedef void (*terminateClispinnerFt) (clispinnert **self);
+typedef char* (*toStringClispinnerFt) (clispinnert *self);
+typedef clispinnert* (*duplicateClispinnerFt) (clispinnert *self);
+typedef void (*smashClispinnerFt) (clispinnert **self);
+
+/**
+ * free clispinner
+ */
+typedef void (*finishClispinnerFt) (clispinnert **self);
+
+typedef void (*startClispinnerFt) (clispinnert *self);
+typedef void (*stopClispinnerFt) (clispinnert *self);
+typedef void (*createTheSignalTimerClispinnerFt)(clispinnert *self);
+typedef void (*setSignalTimerClispinnerFt) (clispinnert *self, signalTimert * signalTimer);
+typedef signalTimert* (*getSignalTimerClispinnerFt) (clispinnert *self);
+typedef void (*pauseProcessClispinnerFt) (clispinnert *self);
+typedef void (*setSpinStringClispinnerFt) (clispinnert *self, const char *spinString);
+typedef void (*setIntervalClispinnerFt) (clispinnert *self, u64 interval);
+typedef bool (*isSpinningClispinnerFt) (clispinnert *self);
+
+#define CLISPINNERTITLESIZE 1024
+
+/**
+ * class functions
+ * allocated once for all objects
+ *
+ * freed with finalizeClispinner
+ */
+
+/**
+ * use this define in child classes and add the new function after this class functions
+ *
+ * in this define, add the methods after <finishClispinnerFt finish;>
+ *
+ * Example:
+ * #define RINGFUNCTIONST \n * CLISPINNERFUNCTIONST; \n * setSizeRingFt setSize
+ */
+#define CLISPINNERFUNCTIONST \
+ startClispinnerFt start;\
+ stopClispinnerFt stop;\
+ createTheSignalTimerClispinnerFt createTheSignalTimer;\
+ setSignalTimerClispinnerFt setSignalTimer;\
+ getSignalTimerClispinnerFt getSignalTimer;\
+ pauseProcessClispinnerFt pauseProcess;\
+ setSpinStringClispinnerFt setSpinString;\
+ setIntervalClispinnerFt setInterval;\
+ isSpinningClispinnerFt isSpinning;
+
+
+typedef struct {
+ freeClispinnerFt free;
+ terminateClispinnerFt terminate;
+ toStringClispinnerFt toString;
+ duplicateClispinnerFt duplicate;
+ smashClispinnerFt smash;
+ finishClispinnerFt finish;
+ CLISPINNERFUNCTIONST;
+} clispinnerFunctionst;
+
+/**
+ * class
+ */
+struct clispinner {
+ const char *type;
+ clispinnerFunctionst *f;
+ bool isSpinning;
+ indexer ix;
+ u64 interval;
+ char title[CLISPINNERTITLESIZE];
+ char spinString[32];
+};
+
+/* clispinner */
+
+#define createClispinner(obj) clispinnert obj; initiateClispinner(&obj)
+#define createAllocateClispinner(obj) clispinnert *obj; initiateAllocateClispinner(&obj)
+
+void initiateClispinner(clispinnert *self);
+void initiateAllocateClispinner(clispinnert **self);
+void finalizeClispinner(void);
+
+/* initialize class methods, call registerMethodsClispinner from classes inheriting this class */
+void registerMethodsClispinner(clispinnerFunctionst *f);
+
+clispinnert* allocClispinner(u64 interval, const char *title);
+
+/* end class clispinner*/
diff --git a/clispinnerInternal.h b/clispinnerInternal.h
@@ -0,0 +1,3 @@
+#pragma once
+
+static clispinnerFunctionst *clispinnerF = NULL;
diff --git a/package.yml b/package.yml
@@ -0,0 +1,18 @@
+---
+ name: clispinner
+ version: 0.0.2
+ description: "A simple cli spinner."
+ bin: ./clispinner.c
+ repository:
+ type: git
+ url: git+https://github.com/RemyNoulin/clispinner.git
+ keywords:
+ - utility
+ - cli
+ author: Remy
+ license: MIT
+ bugs:
+ url: https://github.com/RemyNoulin/clispinner/issues
+ homepage: https://github.com/RemyNoulin/clispinner#readme
+ dependencies:
+ signalTimer:
diff --git a/test.c b/test.c
@@ -0,0 +1,55 @@
+#! /usr/bin/env sheepy
+/* or direct path to sheepy: #! /usr/local/bin/sheepy */
+
+#include "libsheepyObject.h"
+#include "clispinner.h"
+
+/* signalTimert theSignalTimer; */
+
+int argc; char **argv;
+
+int main(int ARGC, char** ARGV) {
+
+ argc = ARGC; argv = ARGV;
+
+ initLibsheepy(argv[0]);
+
+ puts("C template");
+ /* initiateSignalTimer(&theSignalTimer); */
+
+ clispinnert *sp = allocClispinner(50, "processing.. ");
+ //setSpinStringG(sp, ".oO'Oo.");
+ setSpinStringG(sp, ".oO@*");
+ setIntervalG(sp, 150);
+ /* createAllocateClispinner(sp); */
+ /* setSignalTimerG(sp, &theSignalTimer); */
+ /* createTheSignalTimerG(sp); */
+
+ startG(sp);
+
+ i16 c = 0;
+ while(1) {
+ /* theSignalTimer.f->pauseProcess(&theSignalTimer); */
+ pauseProcessG(sp);
+ c++;
+ if (c == 60) break;
+ }
+
+ stopG(sp);
+ logVarG(isSpinningG(sp));
+ put;
+
+ startG(sp);
+
+ c = 0;
+ while(1) {
+ /* theSignalTimer.f->pauseProcess(&theSignalTimer); */
+ pauseProcessG(sp);
+ c++;
+ if (c == 20) break;
+ }
+
+ logVarG(isSpinningG(sp));
+ terminateG(sp);
+
+}