Moved registration processing into Frame/Action

This commit is contained in:
Deon George 2019-07-14 22:43:31 +10:00
parent 264747e2f3
commit aa6b2f3244
9 changed files with 316 additions and 217 deletions

View File

@ -66,4 +66,14 @@ abstract class Control
}
abstract public function handle(string $read);
/**
* If completing an Action frame, this will be called to submit the data.
*
* Ideally this should be overridden in a child class.
*/
public function process()
{
$this->complete = TRUE;
}
}

View File

@ -2,11 +2,12 @@
namespace App\Classes\Control;
use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Facades\Validator;
use App\Classes\Control;
use App\Mail\SendToken;
use App\User;
use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Facades\Validator;
/**
* Class Register handles registration
@ -36,35 +37,38 @@ class Register extends Control
*/
public function handle(string $read,array $current=[])
{
// Ignore LF (as a result of pressing ENTER)
if ($read == LF)
return '';
// If we got a # we'll be completing field input.
if ($read == HASH OR $read == LF) {
if ($read == HASH OR $read == CR) {
// Does our field have data...
if (array_get($current['fielddata'],$current['fieldnum'])) {
switch ($current['fieldnum']) {
if ($x=$this->so->fo->getFieldCurrentInput()) {
switch ($this->so->fo->getFieldId()) {
// Username
case 0:
// See if the requested username already exists
if (User::where('login', $current['fielddata'][$current['fieldnum']])->exists()) {
if (User::where('login',$x)->exists()) {
$this->so->sendBaseline($this->so->co,RED.'USER ALREADY EXISTS'.WHITE);
return '';
}
$this->data['user'] = $current['fielddata'][$current['fieldnum']];
$this->so->sendBaseline($this->so->co,GREEN.'Enter Real Name'.WHITE);
break;
// Real Name
case 1:
$this->data['name'] = $current['fielddata'][$current['fieldnum']];
//$this->data['name'] = $x;
$this->so->sendBaseline($this->so->co,GREEN.'Enter Email Address'.WHITE);
break;
// Email Address
case 2:
if (Validator::make(['email'=>$current['fielddata'][$current['fieldnum']]],[
if (Validator::make(['email'=>$x],[
'email'=>'email',
])->fails()) {
$this->so->sendBaseline($this->so->co,RED.'INVALID EMAIL ADDRESS'.WHITE);
@ -73,13 +77,13 @@ class Register extends Control
};
// See if the requested email already exists
if (User::where('email', $current['fielddata'][$current['fieldnum']])->exists()) {
if (User::where('email',$x)->exists()) {
$this->so->sendBaseline($this->so->co,RED.'USER ALREADY EXISTS'.WHITE);
return '';
}
$this->data['email'] = $current['fielddata'][$current['fieldnum']];
$this->data['email'] = $x;
$this->data['token'] = sprintf('%06.0f',rand(0,999999));
$this->so->sendBaseline($this->so->co,YELLOW.'PROCESSING...'.WHITE);
@ -97,14 +101,14 @@ class Register extends Control
// Enter Password
case 3:
$this->data['password'] = $current['fielddata'][$current['fieldnum']];
$this->data['password'] = $x;
$this->so->sendBaseline($this->so->co,GREEN.'Confirm Password'.WHITE);
break;
// Confirm Password
case 4:
if ($this->data['password'] !== $current['fielddata'][$current['fieldnum']]) {
if ($this->data['password'] !== $x) {
$this->so->sendBaseline($this->so->co,RED.'PASSWORD DOESNT MATCH, *09 TO START AGAIN'.WHITE);
return '';
@ -116,19 +120,20 @@ class Register extends Control
// Enter Location
case 5:
$this->data['location'] = $current['fielddata'][$current['fieldnum']];
$this->so->sendBaseline($this->so->co,GREEN.'Enter TOKEN emailed to you'.WHITE);
break;
// Enter Token
case 6:
if ($this->data['token'] !== $current['fielddata'][$current['fieldnum']]) {
if ($this->data['token'] !== $x) {
$this->so->sendBaseline($this->so->co,RED.'TOKEN DOESNT MATCH, *09 TO START AGAIN'.WHITE);
return '';
}
$this->complete = TRUE;
break;
default:
@ -150,31 +155,4 @@ class Register extends Control
return $read;
}
public function process()
{
$o = new User;
try {
$o->login = $this->data['user'];
$o->email = $this->data['email'];
$o->password = $this->data['password'];
$o->name = $this->data['name'];
$o->location = $this->data['location'];
$o->save();
$this->so->sendBaseline($this->so->co,GREEN.'ACCOUNT CREATED, PRESS '.HASH.' TO CONTINUE...'.WHITE);
$this->state['action'] = ACTION_NEXT;
// Add to CUG 0
$o->cugs()->attach(0);
} catch (\Exception $e) {
$this->so->sendBaseline($this->so->co,RED.'SOMETHING WENT WRONG...'.WHITE);
$this->so->log('error',$e->getMessage());
$this->state['action'] = ACTION_RELOAD;
}
$this->complete = TRUE;
}
}

View File

@ -2,8 +2,7 @@
namespace App\Classes;
use Illuminate\Support\Collection;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Arr;
use App\User;
use App\Models\{CUG,Mode};
@ -41,6 +40,12 @@ abstract class Frame
// This holds the frame object as retrieved from the DB
protected $fo = NULL;
// Current field being edited
private $field_active = FALSE;
// Current input data for fields
private $field_data = [];
/*
// All this vars should be overridden in the child class
protected $frame_length = 22;
@ -65,7 +70,7 @@ abstract class Frame
];
// @todo Move this to the database
private $header = RED.'T'.BLUE.'E'.GREEN.'S'.YELLOW.'T'.MAGENTA.'!';
private $header = RED.SPACE.'T'.BLUE.SPACE.'E'.GREEN.SPACE.'S'.YELLOW.SPACE.'T'.MAGENTA.SPACE.'!';
public function __construct(FrameModel $o)
{
@ -83,6 +88,9 @@ abstract class Frame
// Our parser object
$this->po = $this->parser($startline);
// Set our first editable field
$this->resetCurrentField();
}
/**
@ -186,10 +194,44 @@ abstract class Frame
/**
* Return the current field configuration
* Will return false if no id specified and the current field is not active
*/
public function getField(int $id)
public function getField(int $id=NULL)
{
return $this->fields()->get($id);
if (is_null($id) AND $this->field_active === FALSE)
return FALSE;
return $this->fields()->get(is_null($id) ? $this->field_active : $id);
}
/**
* Get the input for the current field
*
* @return mixed
*/
public function getFieldCurrentInput()
{
return Arr::get($this->field_data,$this->field_active);
}
public function getFieldData()
{
return $this->field_data;
}
public function getFieldDataId(int $id)
{
return Arr::get($this->field_data,$id);
}
/**
* Return the current field ID
*
* @return bool
*/
public function getFieldId()
{
return $this->field_active;
}
/**
@ -199,7 +241,7 @@ abstract class Frame
* @param int $after
* @return mixed
*/
public function getFieldId($type='edit',$after=0)
public function getFieldNextId($type='edit',$after=0)
{
return $this->fields()
->search(function($item,$key) use ($type,$after) {
@ -207,9 +249,16 @@ abstract class Frame
});
}
public function getFieldOptions(int $id)
public function getFieldPrevId($type='edit',$before=FALSE)
{
return array_get($this->fieldoptions,$this->getField($id)->type);
if (! $before)
$before = $this->fields()->count();
return $this->fields()
->reverse()
->search(function($item,$key) use ($type,$before) {
return $key < $before AND $this->isFieldEditable($item->type);
});
}
/**
@ -278,19 +327,28 @@ abstract class Frame
}
/**
* Determine if a field is editable
* Determine if the current field should be masked during input
*
* @param string $field
* @return mixed
*/
public function isFieldEditable(string $field)
public function isFieldCurrentMask(int $id=NULL): string
{
return array_get(array_get($this->fieldoptions,$field),'edit',FALSE);
if (! $x=$this->getField($id))
return FALSE;
return array_get(array_get($this->fieldoptions,$x->type),'mask','');
}
public function isFieldMasked(string $field)
/**
* Determine if a field is editable
*
* @param string $field
* @return boolean
*/
public function isFieldEditable(string $field): bool
{
return array_get(array_get($this->fieldoptions,$field),'mask',FALSE);
return array_get(array_get($this->fieldoptions,$field),'edit',FALSE);
}
/**
@ -349,11 +407,11 @@ abstract class Frame
throw new \Exception('Price too high');
if ($cost > 100)
$color = RED;
$color = RED.SPACE;
elseif ($cost > 0)
$color = YELLOW;
$color = YELLOW.SPACE;
else
$color = GREEN;
$color = GREEN.SPACE;
return sprintf($color.'% '.static::$cost_length.'.0f%s',$cost,static::$cost_unit);
}
@ -387,7 +445,26 @@ abstract class Frame
if (strlen($frame) !== 1)
throw new \Exception('Frame invalid',500);
return WHITE.$num.$frame.(str_repeat(' ',static::$pagenum_length-strlen($num)));
return WHITE.SPACE.$num.$frame.(str_repeat(' ',static::$pagenum_length-strlen($num)));
}
/**
* Reset the current active field to the first one
*/
public function resetCurrentField()
{
$this->field_active = $this->getFieldNextId('edit',0);
$this->resetCurrentFieldData();
}
/**
* Clear the current field
*/
public function resetCurrentFieldData()
{
if ($this->field_active !== FALSE AND isset($this->field_data[$this->field_active]))
unset($this->field_data[$this->field_active]);
}
/**
@ -410,6 +487,61 @@ abstract class Frame
return $this->fo->route->{$key};
}
/**
* Set the field that is current in focus for input
*
* @param int $num
*/
public function setFieldCurrent(int $num)
{
$this->po->field_active = $num;
}
public function setFieldCurrentInput(string $read)
{
if ($this->field_active === FALSE)
throw new \Exception('No field active?',500);
if (! array_key_exists($this->field_active,$this->field_data))
$this->field_data[$this->field_active] = '';
$this->field_data[$this->field_active] .= $read;
}
/**
* Delete the last character of the current Input field
*
* @return bool
*/
public function setFieldCurrentInputDelete(): bool
{
if (! $this->field_data[$this->field_active])
return FALSE;
$this->field_data[$this->field_active] = substr($this->field_data[$this->field_active],0,-1);
return TRUE;
}
/**
* Set the next active field
*/
public function setFieldNext()
{
$this->field_active = $this->getFieldNextId('edit',$this->field_active+1);
$this->resetCurrentFieldData();
}
/**
* Set the previous active field
*/
public function setFieldPrev()
{
$this->field_active = $this->getFieldPrevId('edit',$this->field_active);
$this->resetCurrentFieldData();
}
/**
* Calculate the length of text
*

View File

@ -34,5 +34,5 @@ abstract class Action
return $o;
}
abstract public function handle(array $fielddata);
abstract public function handle();
}

View File

@ -16,10 +16,10 @@ class Login extends Action
* @param array $fielddata
* @return bool
*/
public function handle(array $fielddata)
public function handle()
{
// First field data element is user, the second is the password
if (count($fielddata) != 2 OR ! array_get($fielddata,0) OR ! array_get($fielddata,1))
if (count($this->so->fo->getFieldData()) != 2 OR ! $this->so->fo->getFieldDataId(0) OR ! $this->so->fo->getFieldDataId(1))
{
$this->mode = 2; // MODE_FIELD
// $this->action = 2; // ACTION_GOTO
@ -30,7 +30,7 @@ class Login extends Action
}
try {
$this->uo = User::where('login',array_get($fielddata,0))->firstOrFail();
$this->uo = User::where('login',$this->so->fo->getFieldDataId(0))->firstOrFail();
} catch (ModelNotFoundException $e) {
$this->so->sendBaseline($this->so->co,RED.'USER NOT FOUND, TRY AGAIN *00');
@ -38,7 +38,7 @@ class Login extends Action
return FALSE;
}
if ($this->uo->password != array_get($fielddata,1))
if ($this->uo->password != $this->so->fo->getFieldDataId(1))
{
$this->uo = new User;
$this->so->sendBaseline($this->so->co,RED.'INVALID PASSWORD, TRY AGAIN *00');

View File

@ -0,0 +1,47 @@
<?php
namespace App\Classes\Frame\Action;
use App\User;
use App\Classes\Frame\Action;
/**
* Class Register
* This handles the data received for account registration
*
* @package App\Classes\Frame\Action
*/
class Register extends Action
{
/**
* Handle user logins
*
* @param array $fielddata
* @return bool
*/
public function handle()
{
$o = new User;
try {
$o->login = $this->so->fo->getFieldDataId(0);
$o->name = $this->so->fo->getFieldDataId(1);
$o->email = $this->so->fo->getFieldDataId(2);
$o->password = $this->so->fo->getFieldDataId(3);
$o->location = $this->so->fo->getFieldDataId(5);
$o->save();
$this->so->sendBaseline($this->so->co,GREEN.'ACCOUNT CREATED, PRESS '.HASH.' TO CONTINUE...'.WHITE);
$this->state['action'] = ACTION_NEXT;
// Add to CUG 0
$o->cugs()->attach(0);
} catch (\Exception $e) {
$this->so->sendBaseline($this->so->co,RED.'SOMETHING WENT WRONG...'.WHITE);
$this->so->log('error',$e->getMessage());
$this->state['action'] = ACTION_RELOAD;
}
}
}

View File

@ -10,8 +10,11 @@ abstract class Parser
// Fields in the frame
public $fields = [];
// Parsed frame, ready to send to client
public $output = '';
// Magic Fields that are pre-filled
protected $fieldmap = [
'a'=>'address#',
'd'=>'%date',
];
// Position array of frame control chars
protected $frame_data = [];
@ -19,11 +22,8 @@ abstract class Parser
// Position array of frame chars
protected $frame_content = [];
// Magic Fields that are pre-filled
protected $fieldmap = [
'a'=>'address#',
'd'=>'%date',
];
// Parsed frame, ready to send to client
public $output = '';
public function __construct(string $content,int $width,int $startline=1)
{

View File

@ -76,21 +76,21 @@ abstract class Server {
define('TCP_OPT_LINEMODE', chr(34));
// Status messages
define('MSG_SENDORNOT', GREEN.'KEY 1 TO SEND, 2 NOT TO SEND');
define('MSG_SENT', GREEN.'MESSAGE SENT - KEY '.HASH.' TO CONTINUE');
define('MSG_NOTSENT', GREEN.'MESSAGE NOT SENT - KEY '.HASH.' TO CONTINUE');
define('MSG_SENDORNOT', GREEN.SPACE.'KEY 1 TO SEND, 2 NOT TO SEND');
define('MSG_SENT', GREEN.SPACE.'MESSAGE SENT - KEY '.HASH.' TO CONTINUE');
define('MSG_NOTSENT', GREEN.SPACE.'MESSAGE NOT SENT - KEY '.HASH.' TO CONTINUE');
define('ERR_DATABASE', RED.'UNAVAILABLE AT PRESENT - PLS TRY LATER');
define('ERR_NOTSENT', WHITE.'MESSAGE NOT SENT DUE TO AN ERROR');
define('ERR_PRIVATE', WHITE.'PRIVATE PAGE'.GREEN.'- FOR EXPLANATION *37'.HASH.'..');
define('ERR_ROUTE', WHITE.'MISTAKE?'.GREEN.'TRY AGAIN OR TELL US ON *08');
define('ERR_DATABASE', RED.SPACE.'UNAVAILABLE AT PRESENT - PLS TRY LATER');
define('ERR_NOTSENT', RED.SPACE.'MESSAGE NOT SENT DUE TO AN ERROR');
define('ERR_PRIVATE', WHITE.SPACE.'PRIVATE PAGE'.GREEN.SPACE.'- FOR EXPLANATION *37'.HASH.'..');
define('ERR_ROUTE', WHITE.SPACE.'MISTAKE?'.GREEN.SPACE.'TRY AGAIN OR TELL US ON *08');
define('ERR_PAGE',ERR_ROUTE);
define('ERR_USER_ALREADYMEMBER', RED.'ALREADY MEMBER OF CUG');
define('ERR_USER_ALREADYMEMBER', RED.SPACE.'ALREADY MEMBER OF CUG');
define('MSG_TIMEWARP_ON', WHITE.'TIMEWARP ON'.GREEN.'VIEW INFO WITH *02');
define('MSG_TIMEWARP_OFF', WHITE.'TIMEWARP OFF'.GREEN.'VIEWING DATE IS FIXED');
define('MSG_TIMEWARP_TO', GREEN.'TIMEWARP TO %s');
define('MSG_TIMEWARP', WHITE.'OTHER VERSIONS EXIST'.GREEN.'KEY *02 TO VIEW');
define('MSG_TIMEWARP_ON', WHITE.SPACE.'TIMEWARP ON'.GREEN.SPACE.'VIEW INFO WITH *02');
define('MSG_TIMEWARP_OFF', WHITE.SPACE.'TIMEWARP OFF'.GREEN.SPACE.'VIEWING DATE IS FIXED');
define('MSG_TIMEWARP_TO', GREEN.SPACE.'TIMEWARP TO %s');
define('MSG_TIMEWARP', WHITE.SPACE.'OTHER VERSIONS EXIST'.GREEN.SPACE.'KEY *02 TO VIEW');
}
/**
@ -154,13 +154,8 @@ abstract class Server {
$method = collect(); // Method in control for CONTROL_METHOD
$current = []; // Attributes about the current page
// field/fieldnum indexes are for fields on the active page
$current['fieldreset'] = FALSE; // Flag to reset position (used in fields)
$current['fieldpos'] = 0; // For current field, position within.
$current['prevmode'] = FALSE; // Previous mode - in case we need to go back to MODE_FIELD
$fielddata = [];
// @todo Get the login/start page, and if it is not available, throw the ERR_DATEBASE error.
if (isset($config['loginpage'])) {
$next_page = ['frame'=>$config['loginpage']];
@ -202,7 +197,7 @@ abstract class Server {
}
}
if ($control AND $method->count()) {
if ($mode != MODE_BL AND $control AND $method->count()) {
printf("= Start CONTROL: Going to method: %s\n",get_class($method->last()));
// Capture our state when we enter this method.
@ -257,7 +252,7 @@ abstract class Server {
// If we are the main login screen, see if it is a new user
if ($this->fo->isCUG(0))
{
if ($current['field']->type == 't' AND array_get($fielddata,$current['fieldnum']) == 'NEW')
if ($this->fo->getField()->type == 't' AND $this->fo->getFieldCurrentInput() == 'NEW')
{
$action = ACTION_GOTO;
$next_page = ['frame'=>'981']; // @todo This should be in the DB.
@ -273,28 +268,17 @@ abstract class Server {
case Frame::FRAMETYPE_ACTION:
switch ($read) {
// End of field entry.
case LF:
case CR:
case HASH:
// Next Field
$current['fieldnum']++;
$current['fieldpos'] = 0;
$this->fo->setFieldNext();
if ($current['fieldnum'] < $this->fo->fields()->count()) {
$current['fieldnum'] = $this->fo->getFieldId('edit',$current['fieldnum']);
if ($current['fieldnum'] !== FALSE) {
$current['field'] = $this->fo->getField($current['fieldnum']);
$client->send($this->moveCursor($current['field']->x,$current['field']->y).CON);
$mode = MODE_FIELD;
// There were no (more) editable fields.
} else {
$action = ACTION_SUBMITRF;
}
if ($x=$this->fo->getField()) {
$client->send($this->moveCursor($x->x,$x->y).CON);
$mode = MODE_FIELD;
// Finished all editable fields.
} else {
// Finished all editable fields.
$action = ACTION_SUBMITRF;
}
@ -303,63 +287,12 @@ abstract class Server {
case STAR:
$current['prevmode'] = MODE_FIELD;
$action = ACTION_STAR;
$current['fieldpos'] = 0;
$fielddata[$current['fieldnum']] = '';
$current['fielddata'][$current['fieldnum']] = '';
break;
case KEY_DELETE:
if ($current['fieldpos'])
{
$current['fieldpos']--;
if ($this->fo->setFieldCurrentInputDelete())
$client->send(LEFT.$this->fo::$if_filler.LEFT);
$fielddata[$current['fieldnum']] = substr($fielddata[$current['fieldnum']],0,-1);
$current['fielddata'][$current['fieldnum']] = substr($current['fielddata'][$current['fieldnum']],0,-1);
}
break;
case KEY_LEFT:
if ($current['fieldpos']) {
$current['fieldpos']--;
$client->send(LEFT);
}
break;
case KEY_RIGHT:
if ($current['fieldpos']++ < $current['field']->length)
$client->send(RIGHT);
break;
case KEY_DOWN:
if ($current['fieldpos'] + 40 < $current['field']->length) {
$client->send(DOWN);
$current['fieldpos'] = $current['fieldpos'] + 40;
};
break;
case KEY_UP:
if ($current['fieldpos'] - 40 >= 0) {
$client->send($read);
$current['fieldpos'] = $current['fieldpos'] - 40;
};
break;
case CR:
// On second or later line of a field
if ($current['fieldpos'] + $current['field']->x > 40) {
$client->send($read);
$current['fieldpos'] = (($current['fieldpos'] + $current['field']->x) % 40) * 40;
} else {
$client->send($this->moveCursor($current['field']->x,$current['field']->y).CON);
$current['fieldpos'] = 0;
}
break;
@ -368,18 +301,10 @@ abstract class Server {
// Record Data Entry
default:
if (ord($read) > 31 && $current['fieldpos'] < $current['field']->length) {
if (! array_key_exists($current['fieldnum'],$current['fielddata'])) {
$current['fielddata'][$current['fieldnum']] = '';
$fielddata[$current['fieldnum']] = '';
}
if (ord($read) > 31 && strlen($this->fo->getFieldCurrentInput()) < $this->fo->getField()->length) {
$this->fo->setFieldCurrentInput($read);
$fielddata[$current['fieldnum']]{$current['fieldpos']} = $read; // @todo delete
$current['fielddata'][$current['fieldnum']]{$current['fieldpos']} = $read;
$current['fieldpos']++;
$client->send($this->fo->isFieldMasked($current['field']->type) ?: $read);
$client->send($this->fo->isFieldCurrentMask() ?: $read);
}
}
@ -407,7 +332,7 @@ abstract class Server {
$mode = MODE_RFSENT;
} elseif ($ao = FrameClass\Action::factory($this->fo->route(1),$this,$user,$action,$mode)) {
$ao->handle($fielddata);
$ao->handle();
$mode = $ao->mode;
$action = $ao->action;
@ -430,6 +355,7 @@ abstract class Server {
break;
case '2':
// @todo Check if HASH is a valid next destination
$this->sendBaseline($client,MSG_NOTSENT);
$mode = MODE_RFNOTSENT;
@ -601,7 +527,6 @@ abstract class Server {
}
// Toggle Timewarp Mode
// @todo in forms, the cursor is in the wrong location for ANSI
if ($cmd === '01') {
$client->send(COFF);
$timewarp = !$timewarp;
@ -609,11 +534,20 @@ abstract class Server {
$cmd = '';
$action = $mode = FALSE;
if ($current['prevmode'] == MODE_FIELD) {
$mode = $current['prevmode'];
$current['prevmode'] = FALSE;
if ($x=$this->fo->getField()) {
// @todo This WHITE should be removed, and the color set to whatever is in the frame
$client->send($this->moveCursor($x->x+strlen($this->fo->getFieldCurrentInput()),$x->y).CON.WHITE);
}
}
break;
}
// Present Timewarp Frames
// @todo in forms, the cursor is in the wrong location for ANSI
if ($cmd === '02') {
$client->send(COFF);
$action = ACTION_INFO;
@ -671,10 +605,16 @@ abstract class Server {
$mode = $current['prevmode'];
$current['prevmode'] = FALSE;
// @todo The cursor color could be wrong
$client->send($this->moveCursor($current['field']->x,$current['field']->y).CON);
$client->send(str_repeat($this->fo::$if_filler,$current['field']->length));
$current['fieldreset'] = TRUE;
if (! $this->fo->getField())
$this->fo->setFieldPrev();
if ($x=$this->fo->getField()) {
// @todo This WHITE should be removed, and the color set to whatever is in the frame
$client->send($this->moveCursor($x->x,$x->y).CON.WHITE);
$client->send(str_repeat($this->fo::$if_filler,$x->length));
$client->send($this->moveCursor($x->x,$x->y));
$this->fo->resetCurrentFieldData();
}
} else {
$mode = FALSE;
@ -696,7 +636,10 @@ abstract class Server {
// Our method count should be zero
if ($method->count())
dd($method);
{
dump($method);
throw new \Exception('Method count should be zero, but its not...',500);
}
}
// Nothing typed between * and #
@ -829,8 +772,10 @@ abstract class Server {
// We need this extra test in case we come from ACTION_BACKUP
if ($action == ACTION_NEXT)
{
$current['page']['index'] = $this->fo->index();
$next_page = ['frame'=>$this->fo->frame(),'index'=>$this->fo->index_next()];
$next_page = [
'frame'=>$this->fo->frame(),
'index'=>$this->fo->index_next()
];
}
// Look for requested page - charge for it to be loaded.
@ -917,7 +862,6 @@ abstract class Server {
$history->push($next_page);
}
$current['fieldpos'] = 0;
$this->fo = $fo;
$fo = NULL;
$next_page = NULL;
@ -965,27 +909,21 @@ abstract class Server {
// Active Frame. Prestel uses this for a Response Frame.
case Frame::FRAMETYPE_ACTION:
$client->send($output);
// holds data entered by user.
$fielddata = [];
$current['fielddata'] = [];
if ($this->fo->fields()->count()) {
// Get our first editable field.
$current['fieldnum'] = $this->fo->getFieldId('edit',0);
$current['field'] = $this->fo->getField($current['fieldnum']);
$current['fieldreset'] = TRUE;
$this->fo->resetCurrentField();
if ($current['fieldnum'] !== FALSE) {
if ($x=$this->fo->getField()) {
$mode = MODE_FIELD;
// @todo This WHITE should be removed, and the color set to whatever is in the frame
$client->send($this->moveCursor($x->x,$x->y).CON.WHITE);
// There were no editable fields.
// There were no editable fields.
} else {
$mode = MODE_COMPLETE;
$client->send(COFF);
}
$current['fieldpos'] = 0;
} else {
$mode = FALSE;
}
@ -1018,7 +956,7 @@ abstract class Server {
if (count($alts)) {
$n = 1;
$output .= $this->moveCursor(0,$y++).WHITE.NEWBG.RED.'ALTERNATIVE VERSIONS:'.str_repeat(' ',16);
$output .= $this->moveCursor(0,$y++).WHITE.SPACE.NEWBG.RED.'ALTERNATIVE VERSIONS:'.str_repeat(' ',16);
foreach ($alts as $o) {
$date = $o->created_at->format('d M Y');
@ -1026,10 +964,10 @@ abstract class Server {
$line = WHITE.NEWBG;
if ($timewarp) {
$line .= RED.$n++;
$line .= RED.SPACE.$n++;
}
$line .= BLUE.$date.' '.$o->note;
$line .= BLUE.SPACE.$date.' '.$o->note;
$output .= $this->moveCursor(0,$y++).$line.str_repeat(' ',40-$this->fo->strlenv($line)); // @todo should use frame::page_length
}
@ -1052,12 +990,6 @@ abstract class Server {
serialize($action),
$control);
// We need to reposition the cursor to the current field.
if ($current['fieldreset'] !== FALSE) {
$client->send($this->moveCursor($current['field']->x,$current['field']->y).CON);
$current['fieldreset'] = FALSE;
}
// Did the client disconnect
if ($read === NULL || socket_last_error()) {
$client->close();

View File

@ -24,26 +24,26 @@ class Ansi extends AbstractServer {
define('CLS', ESC.'[2J');
define('HASH', '#'); // Enter
define('STAR', '*'); // Star Entry
define('SPACE', ' '); // Space
define('SPACE', ' '); // Space (for compatibility with Videotex)
// NOTE: This consts are effective output
define('RED', ESC.'[0;31m'.SPACE);
define('GREEN', ESC.'[0;32m'.SPACE);
define('YELLOW', ESC.'[1;33m'.SPACE);
define('BLUE', ESC.'[0;34m'.SPACE);
define('MAGENTA', ESC.'[0;35m'.SPACE);
define('CYAN', ESC.'[0;36m'.SPACE);
define('WHITE', ESC.'[1;37m'.SPACE);
define('RED', ESC.'[0;31m');
define('GREEN', ESC.'[0;32m');
define('YELLOW', ESC.'[1;33m');
define('BLUE', ESC.'[0;34m');
define('MAGENTA', ESC.'[0;35m');
define('CYAN', ESC.'[0;36m');
define('WHITE', ESC.'[1;37m');
define('NEWBG', '');
// Raw attributes - used when storing frames.
define('R_RED', RED);
define('R_GREEN', GREEN);
define('R_YELLOW', YELLOW);
define('R_BLUE', BLUE);
define('R_MAGENTA', MAGENTA);
define('R_CYAN', CYAN);
define('R_WHITE', WHITE);
// Compatibility attributes (to Videotex).
define('R_RED', RED.SPACE);
define('R_GREEN', GREEN.SPACE);
define('R_YELLOW', YELLOW.SPACE);
define('R_BLUE', BLUE.SPACE);
define('R_MAGENTA', MAGENTA.SPACE);
define('R_CYAN', CYAN.SPACE);
define('R_WHITE', WHITE.SPACE);
//define('FLASH',chr(8));
// Keyboard presses