PowerBuilder Datawindow EditMask for IP Address - ip

Please help me for writing datawindow editmask for IP address. Currently I am doing like this
###.###.###.### but it can also allow 300.300.300.300, and a valid ip address only allows maximum 255.255.255.255. Please guide me. Thanks

You can't.
You'll have to create an user event using pbm_keydown or pbm_downkey as event id and write a script to stop keystrokes from being allowed. The return value allows you to deny that key or not.

Edit masks don't validate input they just format it. You might be better off using the itemchanged event to validate the data.

your edit mask is okay,
If I were you, I will define 4 number column in the datawindow
howerver, if you want validation, you need to code in itemchanged event:
ls_colname = dw_1.GetcolumnName()
Choose Case ls_colname
Case "subnet_msk_1"
if Integer(dw_1.getText()) > 255
MessageBox("Warning", "Incorrect Input, subnet mask value should not be > 255")
/*this will not let the datawindow accept the invalid input*/
return 1
end if
Case "subnet_msk_2"
/*do the same*/
Case "subnet_msk_3"
/*do the same*/
Case "subnet_msk_4"
/*do the same*/
/*write your logic here*/
End Choose
If you want to use only 1 String cloumn, I believe that you will need to use the mid() function, just press F1 in PB, you can find out the examples, in your case:
ls_colname = dw_1.GetcolumnName()
Choose Case ls_colname
Case "subnet_msk"
if Mid(dw_1.getText(), 1, 4) > 255 OR Mid(dw_1.getText(), 4, 8) > 255 /*etc..*/
/*your logic here*/
end if

You can use Match function to validate ip address after user's input:
int i, j
int matchedCount
boolean isValid
String patterns[] = {"^25[0-5]$", "^2[0-4][0-9]$", "^[01]?[0-9][0-9]?$"}
string ip[] = {"162","168","1","1"} // test for success
//string ip[] = {"162","168","256","101"} // test for fail
for i = 1 to 4
for j = 1 to 3
if match(ip[i], patterns[j]) then matchedCount++
next
next
isValid = (matchedCount = 4)
Not optimized, but compact

Related

.Net Core 3 Preview SequenceReader Length Delimited Parsing

I'm trying to use SequenceReader<T> in .Net Core Preview 8 to parse Guacamole Protocol network traffic.
The traffic might look as follows:
5.error,14.some text here,1.0;
This is a single error instruction. There are 3 fields:
OpCode = error
Reason = some text here
Status = 0 (see Status Codes)
The fields are comma delimited (semi-colon terminated), but they also have the length prefixed on each field. I presume that's so that you could parse something like:
5.error,24.some, text, with, commas,1.0;
To produce Reason = some, text, with, commas.
Simple comma delimited parsing is simple enough to do (with or without SequenceReader). However, to utilise the length I've tried the following:
public static bool TryGetNextElement(this ref SerializationContext context, out ReadOnlySequence<byte> element)
{
element = default;
var start = context.Reader.Position;
if (!context.Reader.TryReadTo(out ReadOnlySequence<byte> lengthSlice, Utf8Bytes.Period, advancePastDelimiter: true))
return false;
if (!lengthSlice.TryGetInt(out var length))
return false;
context.Reader.Advance(length);
element = context.Reader.Sequence.Slice(start, context.Reader.Position);
return true;
}
Based on my understanding of the initial proposal, this should work, though also could be simplified I think because some of the methods in the proposal make life a bit easier than that which is available in .Net Core Preview 8.
However, the problem with this code is that the SequenceReader does not seem to Advance as I would expect. It's Position and Consumed properties remain unchanged when advancing, so the element I slice at the end is always an empty sequence.
What do I need to do in order to parse this protocol correctly?
I'm guessing that .Reader here is a property; this is important because SequenceReader<T> is a mutable struct, but every time you access .SomeProperty you are working with an isolated copy of the reader. It is fine to hide it behind a property, but you'd need to make sure you work with a local and then push back when complete, i.e.
var reader = context.Reader;
var start = reader.Position;
if (!reader.TryReadTo(out ReadOnlySequence<byte> lengthSlice,
Utf8Bytes.Period, advancePastDelimiter: true))
return false;
if (!lengthSlice.TryGetInt(out var length))
return false;
reader.Advance(length);
element = reader.Sequence.Slice(start, reader.Position);
context.Reader = reader; // update position
return true;
Note that a nice feature of this is that in the failure cases (return false), you won't have changed the state yet, because you've only been mutating your local standalone clone.
You could also consider a ref-return property for .Reader.

Provide a list of numbers to Alexa

I want to create a lottery skill that takes 6 numbers from the user.
I'm currently learning by going through the samples and developer guides, and I can go through the guides and get a working skill that will take one input and then end the session. But I believe I need to create a dialog somehow, which is where I get stuck.
Design-wise, I'd like the dialog to go like this:
Alexa: Please provide the first number
User: 1
Alexa: and now the second...
User: 2
etc etc
But I think it would be OK if it went like this:
Alexa: Please call out 6 numbers
User: 1, 2, 3, 4, 5, 6.
Is this even possible? Will I have to create a custom slot type called "Numbers" and then put in the numbers, eg 1-50 or whatever the limit is?
At best, I can currently get it to ask for one number, so its really the dialog interaction that I'm stuck on. Has anyone ever even done anything like this?
Thanks.
Yes to both questions. You could string together a response with 6 different custom slots. "User: My numbers are {num1}, {num2}, {num3}, {num4}, {num5}, {num6} " and make them all required using the skills beta developer. However, it will be a rather bad user experience if the user does not phrase their answer appropriately and Alexa has to ask follow up questions to obtain each number. The last problem you'll run into is that while a custom slot could be defined to contain the numbers 1-50 alexa will generally recognize similar values to those provided in a custom slot, such as numbers from 50-99. It would then be up to you to check that the values you receive are between 1 and 50. If not you'd want to ask the user to provide a different number in the appropriate range.
Conclusion: You'll want to have individual interactions where a user provides a single number at a time.
Alexa:"you will be prompted for 6 numbers between 1 and 50 please state them one at a time. Choose your first number."
User:"50"
Alexa:"Your First number is 50, Next number."...
You can implement this using a single intent. let's name that intent GetNumberIntent. GetNumberIntent will have sample uterances along the line of
{number}
pick {number}
choose {number}
where {number} is a custom slot type or simply AMAZON.NUMBER. It will then be up to you to check that the number is between 1 and 50.
I program in Node.js using the SDK. Your implementation may vary depending upon your language choice.
What I would do is define 6 different state handlers. Each handler should have the GetNumberIntent. When a GetNumberIntent is returned if the slot value is apropriate store the value to the session data and or dynamodb and move forward to the next state. If the slot value is invalid stay for example at state "NumberInputFiveStateHandlers" until a good value is received then change state to the next "NumberInputSixStateHandlers"
var NumberInputFiveStateHandlers = Alexa.CreateStateHandler(states.NUMFIVEMODE, {
'NewSession': function () {
this.emit('NewSession'); // Uses the handler in newSessionHandlers
},
//Primary Intents
'GetNumberIntent': function () {
let message = ` `;
let reprompt = ` `;
let slotValue = this.event.request.intent.slots.number.value;
if(parseInt(slotValue) >= 1 && parseInt(slotValue) <= 50){
this.handler.state = states.NUMSIXMODE;
this.attributes['NUMBERFIVE'] = this.event.request.intent.slots.number.value;
message = ` Your fifth number is `+slotValue+`. please select your sixth value. `;
reprompt = ` please select your sixth value. `;
}else{
message = ` The number `+slotValue)+` is not in the desired range between 1 and 50. please select a valid fifth number. `;
reprompt = ` please select your fifth value. `;
}
this.emit(':ask',message,reprompt);
},
//Help Intents
"InformationIntent": function() {
console.log("INFORMATION");
var message = ` You've been asked to choose a lottery number between 1 and 50. Please say your selection.`;
this.emit(':ask', message, message);
},
"AMAZON.StopIntent": function() {
console.log("STOPINTENT");
this.emit(':tell', "Goodbye!");
},
"AMAZON.CancelIntent": function() {
console.log("CANCELINTENT");
this.emit(':tell', "Goodbye!");
},
'AMAZON.HelpIntent': function() {
var message = `You're playing lottery. you'll be picking six numbers to play the game. For help with your current situation say Information. otherwise you may exit the game by saying quit.`;
this.emit(':ask', message, message);
},
//Unhandled
'Unhandled': function() {
console.log("UNHANDLED");
var reprompt = ' That was not an appropriate response. Please say a number between 1 and 50.';
this.emit(':ask', reprompt, reprompt);
}
});
This is an example of the fifth request. You'll have 6 identical states like this one that string back to back. Eventually you'll end up with 6 session values.
this.attributes['NUMBERONE']
this.attributes['NUMBERTWO']
this.attributes['NUMBERTHREE']
this.attributes['NUMBERFOUR']
this.attributes['NUMBERFIVE']
this.attributes['NUMBERSIX']
You can then use these values for your game.
If you have not used the alexa-sdk before you must remember to register your state handlers and add your modes to the states variable.
alexa.registerHandlers(newSessionHandlers, NumberInputOneStateHandlers, ... NumberInputSixStateHandlers);
var states = {
NUMONEMODE: '_NUMONEMODE',
...
...
NUMSIXMODE: '_NUMSIXMODE',
}
This answer is not intended to cover the basics of coding using Alexas-SDK. There are other resourced for more specific questions on that topic.
Alternatively, because your intent is identical [GetNumberIntent], you may be able to get by with a single StateHandler that pushes new valid numbers onto an array until the array is the desired length. That would simply require more logic inside the Intent Handler and a conditional to break out of the state once the array is of length 6.
Try the code above first because it's easier to see the different states.

Unable to read AT Command Response

I test some basic AT Command in Hyperterminal. The GSM modem response as per my command too. But problem is that it shows me the unreadable text. I use the following code :
AT
OK
AT+CUSD=1,"*247#",15
OK
+CUSD: 1,"0062004B006100730068000A00310020004D0032004D0020005400720061006E007300
6600650072000A0032002000440069007300620075007200730065000A00330020004D0079002000
62004B006100730068000A0034002000480065006C0070006C0069006E0065000A",72
AT+CUSD=1,"1",15
OK
AT+CUSD=1,"*247#",15 command should display
Menu 1
Menu 2
Menu 3
Something like that. But it displayed the hexadecimal code which it unreadable. How can I get plain text ? Can anyone help Me ?
Judging by information provided. Where when you send the +CUSD request with DCS (Data Coding Scheme) of 15. And the response from the Bkash service with DCS of 72. It looks like your modem does not support the encoding specified in the DCS from Bkash.
I found is fairly similar question and solution to this question. Try and ensure that +CSCS is set to something like IRA or GSM and see what happens then with your +CUSD responses.
Use the following functions to decode "UCS2" response data:
public static String HexStr2UnicodeStr(String strHex)
{
byte[] ba = Hex2ByteArray(strHex);
return HexBytes2UnicodeStr(ba);
}
public static String HexBytes2UnicodeStr(byte[] ba)
{
var strMessage = Encoding.BigEndianUnicode.GetString(ba, 0, ba.Length);
return strMessage;
}
for example:
String str2 = SmsEngine.HexStr2UnicodeStr("0062004B006100730068000A00310020004D0032004D0020005400720061006E0073006600650072000A0032002000440069007300620075007200730065000A00330020004D007900200062004B006100730068000A0034002000480065006C0070006C0069006E0065000A");
// str2 = "bKash\n1 M2M Transfer\n2 Disburse\n3 My bKash\n4 Helpline\n"
Please also check UnicodeStr2HexStr()
Hi this code is something called PDU (Protocol Data Unit). To decode it is not straight forward. you need to understand the structure first.

Flex Rich Text Editor - Limiting the number of characters

Is there a way to restrict the number
of characters in the Flex Rich Text Editor?
I guess there should be, since it's possible
in a textarea. So, if I could get hold
of the textarea contained in the rich
text editor, I would be able to do it
I think this would be fairly easy in actionscript, although I'm not exactly sure how one would do it in mxml. It appears that there are two children that are contained in the RichTextEditor, one of them being TextArea. According to the documentation (http://livedocs.adobe.com/flex/3/langref/mx/controls/RichTextEditor.html#propertySummary), you can access the subcontrols like so:
myRTE.toolBar2.setStyle("backgroundColor", 0xCC6633);
With myRTE being the instance of your text editor. So my guess would be something like this would work:
myRTE.textArea.maxChars = 125;
With 125 being the number a characters you would want restricted to.
i just ran into this.
setting your maxChars on the textArea will provide a limit to the text area, but that won't be representative of the number of characters the user can type.
as the user is typing, markup is added behind the scenes, and that greatly increases the char count.
for example, if i type the letter 'a' into a RichTextEditor, i get a char count of 142 and this htmlText:
<TEXTFORMAT LEADING="2"><P ALIGN="LEFT"><FONT FACE="Verdana" SIZE="10" COLOR="#0B333C" LETTERSPACING="0" KERNING="0">a</FONT></P></TEXTFORMAT>
i could not see a straightforward way to get a proper maxChar to work out of the box, so i extended RichTextEditor and gave it a maxChar. if maxChar > 0, i added a listener to "change" and did something like this in the event handler:
protected function handleTextChange(event:Event) : void
{
var htmlCount:int = htmlText.length;
// if we're within limits, ensure we reset
if (htmlCount < maxChars)
{
textArea.maxChars = 0;
this.errorString = null;
}
// otherwise, produce an error string and set the component so the user
// can't keep typing.
else
{
var textCount:int = textArea.text.length;
textArea.maxChars = textCount;
var msg:String = "Maximum character count exceeded. " +
"You are using " + htmlCount + " of " + maxChars + " characters.";
this.errorString = msg;
}
}
the idea is to apply a maxChars to the text area only when in the error state, so the user cannot type anything additional and will be prompted to erase some chars. once we leave the error state, we need to set the textArea.maxChars to zero so they can continue.

Keyboard code mapping in Adobe Flash/Flex for the browser

N.B. Keep in mind the difference between key code and character code. For example, the number 1 (one) and the character ! (bang) both have the same key code but different character codes. Likewise, the number 7 from the row of numbers and the number 7 from the numpad have different key codes but the same character codes.
I'm programming a music rhythm game in Adobe Flex and would like to bind keyboard keys. This isn't a problem, but I certainly would have a problem, say, setting the default keys to A, S, D, and F and telling the user that this is the case.
If you take a look at the documentation for flash.ui.Keyboard, you'll see that there are constants for keyboard keys to key codes. However, these are only available in Adobe AIR and not the browser. This makes sense since not all operating systems and keyboards are alike (or present!), so key codes can vary.
So, how can I assign default keys that have meaning instead of picking key codes and praying?
My only sane thought is to store the character codes for the key bindings and then provide an character code to String mapping so I can tell the user what to press. However, my gut tells me that this will break in subtle or not-so-subtle ways. Like CAPSLOCK.
Thanks.
Update: I am currently using radekg's answer, but I still think that this will break easily. I would feel more comfortable with some persuasion that this is correct.
according to Flash 8 documentation you can simply rely on ASCII codes. Take a look at these topics of the Flash 8 documentation:
http://livedocs.adobe.com/flash/mx2004/main_7_2/wwhelp/wwhimpl/common/html/wwhelp.htm?context=Flash_MX_2004&file=00001113.html
http://livedocs.adobe.com/flash/mx2004/main_7_2/wwhelp/wwhimpl/common/html/wwhelp.htm?context=Flash_MX_2004&file=00001115.html#71579
http://livedocs.adobe.com/flash/mx2004/main_7_2/wwhelp/wwhimpl/common/html/wwhelp.htm?context=Flash_MX_2004&file=00001116.html#71709
http://livedocs.adobe.com/flash/mx2004/main_7_2/wwhelp/wwhimpl/common/html/wwhelp.htm?context=Flash_MX_2004&file=00001114.html#71525
As far as I'm aware of all modern operating systems use standard ASCII. These codes have not changed since Flash 5 era. To compare letters if you don't want to rely on ASCII codes:
private function compareChar(code:Number):void {
if ( "a" == String.fromCharCode( code ).toLowerCase() ) {
trace("A pressed");
} else {
trace("You pressed " + String.fromCharCode(code));
}
}
...
compareChar(65); // 65 is A
compareChar(96); // 96 is numpad 0
However I think you can rely on ASCII codes.
Hope this helps.
Radekg is mostly correct.
Flash has a built in Class flash.ui.KeyLocation with four static properties: LEFT, RIGHT, NUM_PAD, STANDARD. This means that you can have a definitive idea which key has been pressed, even if the keyboard has been remapped. If you this in combination with String.fromCharCode, you should be able to solve this problem rather neatly.
Your final code might look like:
import flash.ui.KeyLocation;
import flash.events.KeyboardEvent;
function handleKeyboardEvent( event:KeyboardEvent )
{
// This will work for a majority of the keys.
var key:String = String.fromCharCode( event.charCode ).toLowerCase();
// Use strict comparison
if( event.keyLocation !== KeyLocation.STANDARD )
{
// The key is a number, then it needs to be re-identified.
if( event.keyLocation == KeyLocation.RIGHT ) key = "r" + key;
if( event.keyLocation == KeyLocation.LEFT ) key = "l" + key;
if( event.keyLocation == KeyLocation.NUM_PAD) key = "n" + key;
}
switch( key )
{
case "r1":
// Do something with the one which is not on the keypad.
break;
case "n.":
// Do something with the number pad's period.
break;
case "n":
// Do something with the letter N.
break;
}
}
I will admit, I am not certain what will happen with String.fromCharCode and control keys (F1, Alt, Ctrl, etc), but the KeyboardEvent does support event.shiftKey, event.ctrlKey, event.altKey

Resources