[Orion] world chat buy/sell script

If you make a Client-side script you can publish it here for other players to use
Post Reply
User avatar
MagicUser
Legendary Scribe
Posts: 206
Joined: Mon Nov 03, 2014 2:24 pm
Location: PST

[Orion] world chat buy/sell script

Post by MagicUser »

Prompt
I saw some people were forgetting the spam rules for world chat sell/buy messages. I would love to help make this easier, but I also don't want to make wc an unpleasant space (even if people are following the rules).

Codex Rules.jpg
Codex Rules.jpg (175.6 KiB) Viewed 8585 times

Since the rules are somewhat hard to follow if you don't want to be thinking about it (which I certainly rarely do), I thought perhaps it would be good if I made an Orion script that helps people follow said rule.

How to use
Use:

Code: Select all

_wc "I want to sell 30k ointments for 2k gold each."
You cancel the message with:

Code: Select all

_wc
And you can start a different message at any time with:

Code: Select all

_wc "different message"

Testing

Code: Select all

_wc "I think that I should test this outside of wc before using it and then accidentally spamming wc."

Code: Select all

[01:07:18.194] I think that I should test this outside of wc before using it and then accidentally spamming wc.
(1): [08:56] Arandros: forget up
(2): [09:34] Spacemonk: ok and why i dont get ed from the voting stone, its saying its active and reward --
(3): [09:34] Spacemonk: nice
(4): [09:35] Praise: you start with some gold and it builds to ED after several days
(5): [09:35] Praise: the gold will increase daily until then
(6): [09:36] Praise: if i remember correctly. been a long time for me
(7): [09:36] Spacemonk: i know that, im reward level 25, getting eds many weeks
(8): [09:36] Praise: oh ok
(9): [09:36] Spacemonk: but not now :/
(10): [09:36] Praise: so did you miss a day or a few days?
(11): [09:36] Spacemonk: didnt give me a thing
(12): [09:36] Praise: may have had a set back

[02:36:44.267] I think that I should test this outside of wc before using it and then accidentally spamming wc.
(1): [09:36] Spacemonk: no money no ed
(2): [09:36] Spacemonk: nope
(3): [09:37] Spacemonk: have voted everyday
(4): [09:37] Praise: if you claimed it today it would be in your backpack. that's odd
(5): [09:38] Spacemonk: its showing i didnt get it yet, its showing - - - just like before you push claim reward
(6): [09:38] Praise: do a [mystuff for Excelsior Dollar and see if it shows in your backpack
(7): [09:38] Praise: vote again ?
(8): [09:38] Spacemonk: voted 3 times already
(9): [09:38] Praise: today?
(10): [09:38] arni: vote on more sites it sometimes needs a few
(11): [09:38] Jian yang: anyone selling GoC?
(12): [09:38] Spacemonk: yea cuz it didnt give me a thing

[03:36:44.266] I think that I should test this outside of wc before using it and then accidentally spamming wc.
(1): [11:17] Lisan Al Gaib: My vendor @Old Deckard is restocked w nice gear, weapons, relayers, ed room itens, bc, pwt, pets and + Visit Forum > Market
(2): [12:33] Lisan Al Gaib: My vendor @Old Deckard TC is restocked w nice gear, weapons, relayers, ed room itens, bc, pwt, pets ++ Visit Forum > Market
(3): [12:44] Avacodo: doom champ up
(4): [12:59] Timmatt: ailly question. is there  key command to hide names of things? i think i found it by accidenent somehow
(5): [13:59] Pennywise: is there any LMC around ?
(6): [14:42] Pennywise: Praise around? it's the guy asking who is always harrassing ;D
(7): [14:42] Praise: yes i'm here
(8): [14:45] Matrix: :P
(9): [14:46] Matrix: Let's Make A Deal is Back!
(10): [14:46] Sinja: It is!
(11): [14:46] Praise: yes this Saturday
(12): [14:46] Pennywise: btw does anyone know where is the DLG guild house or even the guild stone ?

[07:46:52.724] I think that I should test this outside of wc before using it and then accidentally spamming wc.
(1): [14:48] Sinja: We have some nice prizes for Let's Make A Deal
(2): [14:48] Sinja: And more than a few ZOINKS too! lol
(3): [14:48] Praise: no i dont
(4): [14:48] Praise: who is the guild leader?
(5): [14:49] Matrix: i have a date all saturday good luck for all deal :P
(6): [14:49] Sinja: awww...we'll miss you Matrix
(7): [14:49] Praise: yes we will!
(8): [14:49] Praise: but even worse... you'll miss us! LOL
(9): [14:50] Sinja: two games ! one at 1400 and one at 2200, maybe you can make one of them
(10): [14:50] Matrix: no worries i can arrange some cookies for event :P
(11): [14:50] Sinja: LOL you always come through in a clutch!
(12): [14:50] Matrix: lol

[08:46:52.848] I think that I should test this outside of wc before using it and then accidentally spamming wc.
(1): [16:30] Funinfel: Just dumped a lot of exceptional  vyumi bows in weapon box at new player area
(2): [16:31] Funinfel: Yumi even
It follows all of the codex rules, I intend to do a live 2-day test at some point to verify that it is working 100% properly.

Discussion
I was talking with Warren about this and he brought up an excellent point. "do you want to be the guy who brings automated spam to the masses?"
I like helping people, but I really don't want to accidentally harm the shard.

This post is to see if I am missing something, if it would be better for me to not post such a script. Of course, if +C were to say that he would prefer that one not be made public, I would not post the script.

pros:
  • Users will be following the codex rules. Any future changes to the rules, can be reflected in the script.
  • Easier for players to make adverts, without thinking too much about it.
  • Players already need to be online to use such a script, so bots are already technically not allowed.
  • Violators are easy to catch.
  • Players have already been doing the same thing in other scripting languages, they're just not as good.
  • You can always ignore a player if you find them annoying.
cons:
  • Automated messaging, can be annoying if employed on a large scale.
  • +C is not always around to catch world chat spam violators.
  • Its not as easy to shame a player who is not online for abusing the rules.
Closing Remarks
Thank you, I am interested in hearing your thoughts, comments, pros, and cons. I'll let this thread stew for a week or two and then decide from there.
Respectfully,
Paroxysmus ILV Master Spellcaster

Image
User avatar
Johnny Warren
Legendary Scribe
Posts: 968
Joined: Mon Oct 11, 2010 11:40 pm

Re: [Orion] world chat buy/sell script

Post by Johnny Warren »

Woohoo... u all thought my spam was bad before...

Looks interesting Proxy.

EDIT: Now that I've actually read the post.... my thoughts...

I don't really care. I barely read WC anyway. My thoughts are generally undesired anyways, so we'll leave it there. :dance
JOHNNY WARREN!
Image
User avatar
Wil
Legendary Scribe
Posts: 1228
Joined: Mon Dec 30, 2013 1:19 pm
Location: Seattle, WA, USA
Contact:

Re: [Orion] world chat buy/sell script

Post by Wil »

MagicUser wrote: Wed Sep 25, 2024 12:58 pm Thank you, I am interested in hearing your thoughts, comments, pros, and cons.
Howdy,

How does your script implement rule #4: the player must be present at the keyboard when posting an announcement?

I could write an OpenEUO script that watches for keypresses and holds scheduled posts until the next keypress, but Orion works differently than OpenEUO. How does *your* script do it?
User avatar
MagicUser
Legendary Scribe
Posts: 206
Joined: Mon Nov 03, 2014 2:24 pm
Location: PST

Re: [Orion] world chat buy/sell script

Post by MagicUser »

It doesn't.
Wil wrote: Wed Sep 25, 2024 7:32 pm How does your script implement rule #4: the player must be present at the keyboard when posting an announcement?
My assumption is that players will behave civilly and follow such a rule. This is the same assumption that would be used for if someone posted an attack script. The script is meant to make following the posted rules easier, but a determined player can always find ways to break the rules. As this is not an executable, players have access to code, which means that they can always find the segment that checks for if a player is online and then comment it out.
Wil wrote: Wed Sep 25, 2024 7:32 pm I could write an OpenEUO script that watches for keypresses and holds scheduled posts until the next keypress, but Orion works differently than OpenEUO. How does *your* script do it?
I could put in a journal check or a gump with a button (1-2 messages without check). It'd wait for the check to proceed with a message.

The button seems like an easier solution, since I'd like to not have to force the user to make a hotkey, and having to type something out sounds tedious for the user.

[edit]:
I implemented the button. Works nicely. Note that the code below is only the online check.

Code: Select all

function create_is_player_active_gump() {
	Shared.AddVar('player_is_active', false);
	
	var gump = Orion.CreateCustomGump(50);
	gump.Clear();
	
	gump.AddText(350, 300, '0x0035', 'Are you online?');
	gump.AddButton(1, 350, 320, '0x00F9', '0x00F7', '0x00F8', 0, 1, 1);
	gump.SetCallback('is_player_active_answer');
	
	gump.Update();
}

function is_player_active_answer() {
	Shared.AddVar('player_is_active', true);
	Orion.CloseGump('custom', 50);
}
Online_Check.jpg
Online_Check.jpg (11.99 KiB) Viewed 8505 times
Respectfully,
Paroxysmus ILV Master Spellcaster

Image
User avatar
Johnny Warren
Legendary Scribe
Posts: 968
Joined: Mon Oct 11, 2010 11:40 pm

Re: [Orion] world chat buy/sell script

Post by Johnny Warren »

I think monitoring if people are at keyboard when entering a WC ad is the least of our concerns regarding cheating/rule violations.

Wait til halloween opens next months and everyone gets their VPNs fired up and the shill accounts come out in force. I could list 5 player names that you won't have seen all year, and all of them will appear, moving their sigils to the main chars vendor. 15 sigils a day is better than 5 I guess... Hoping that +C gets vigilant during this period as it really is when the cheats come out in force...

Sorry, forgot the new rule about derailing threads and staying on topic... :scared: :worried: Um, yeah, as Paroxys said, it's no different to someone posting a [bandself script. You assume they will follow the rules with it and not use it to farm AFK.
JOHNNY WARREN!
Image
User avatar
Wil
Legendary Scribe
Posts: 1228
Joined: Mon Dec 30, 2013 1:19 pm
Location: Seattle, WA, USA
Contact:

Re: [Orion] world chat buy/sell script

Post by Wil »

MagicUser wrote: Wed Sep 25, 2024 11:01 pm
Wil wrote: Wed Sep 25, 2024 7:32 pm How does your script implement rule #4: the player must be present at the keyboard when posting an announcement?
It doesn't. My assumption is that players will behave civilly and follow such a rule.
By remembering to turn it off before they go AFK? Your value proposition for the script was that it relieves users from the chore of having to remember and deal with the specific rules. If it's not doing the AFK part so that they're advertising 24/7 even while they're asleep and not responding to pm's then, respectfully, I'd call that a significant miss for your stated objective.

MagicUser wrote: Wed Sep 25, 2024 11:01 pm I could put in a journal check or a gump with a button (1-2 messages without check). It'd wait for the check to proceed with a message.
I implemented the button. Works nicely. Note that the code below is only the online check.
Yeah, that works, but I'm not keen on a script that randomly raises a gump without attention to what I'm doing at the time.

Johnny Warren wrote: Thu Sep 26, 2024 1:18 am I think monitoring if people are at keyboard when entering a WC ad is the least of our concerns regarding cheating/rule violations.
It's no different to someone posting a [bandself script. You assume they will follow the rules with it and not use it to farm AFK.
I disagree. [bandself doesn't spam other players with messages. If you want to argue equivalence, consider a script that farms mobs on a loop but expects the user to stop it if someone is already at the spawn. So it steals kills if the user looks away or is a little slow on the stop button. Which I hope we all agree would be a bad script.

Regards,
Wil
User avatar
MagicUser
Legendary Scribe
Posts: 206
Joined: Mon Nov 03, 2014 2:24 pm
Location: PST

Re: [Orion] world chat buy/sell script

Post by MagicUser »

Sure, I could put in some no-extra action pulse checks.

Orion has a few functions of interest for this.
Player.Hits, Orion.GetMousePosition, Player.X, Player.Y, Player.Map.

Theoretically, I could check the journal for non-wc messages from you. That might be overkill. If you're moving around, have your status bar changing, or your mouse is moving, seems like that'd cover quite a few cases. Obviously, if you're afk farming you could trigger these checks, but that's a whole nother issue.
Wil wrote: Thu Sep 26, 2024 11:30 pm Yeah, that works, but I'm not keen on a script that randomly raises a gump without attention to what I'm doing at the time.
Respectfully,
Paroxysmus ILV Master Spellcaster

Image
User avatar
Wil
Legendary Scribe
Posts: 1228
Joined: Mon Dec 30, 2013 1:19 pm
Location: Seattle, WA, USA
Contact:

Re: [Orion] world chat buy/sell script

Post by Wil »

MagicUser wrote: Fri Sep 27, 2024 11:53 am Obviously, if you're afk farming you could trigger these checks, but that's a whole nother issue.
Howdy,

Your stated goal is to help honest people stay honest. I think it's reasonable to judge your script on that criteria, not what it can be induced or modified to do if the user wants to defeat it.

Regards,
Wil
User avatar
MagicUser
Legendary Scribe
Posts: 206
Joined: Mon Nov 03, 2014 2:24 pm
Location: PST

Re: [Orion] world chat buy/sell script

Post by MagicUser »

Here is the script. Please let me know if you have any suggestions or find any problems.

How to Use
Type into chat.

Initial message
_wc "Buying sigils for $$k gold."

Changing your message
_wc "Selling sigils for $$$k gold."

Stopping messaging
_wc

Code: Select all

function wc(message) {
	//If a player is launching the script, they are obviously active.
	active_player_answered();
	
	//Make a new message, make a different message, or stop messaging.
	if (!Shared.GetVar('continue_wc_messaging') && message != null) {
		Orion.Exec('handle_wc_message', true, [message]);
	}
	else if (Shared.GetVar('wc_message') != message && message != null) {
		Shared.AddVar('continue_wc_messaging', false);
		while (Orion.ScriptRunning('handle_wc_message') != 0)
			Orion.Wait(50);
		
		Orion.Exec('handle_wc_message', true, [message]);
	}
	else {
		Shared.AddVar('continue_wc_messaging', false);
	}
}

function handle_wc_message(message) {
	Shared.AddVar('continue_wc_messaging', true);
	Shared.AddVar('wc_message', message);
	
	var time_difference = get_time_difference();
	
	var init = true;
	var my_last_msg_time = Orion.Now();
	var my_last_msg_shard_time = "";
	var msg_counter = 0;
	var other_msgs = [];
	var havent_checked_counter = 0;
	var day_change_accounted_for = false;
	while (Shared.GetVar('continue_wc_messaging')) {
		//messages should only be sent if there have been less than 12 sent today, its been an hour, and there have been 12 messages in wc.
		if (init || other_msgs.length == 12 && Math.abs(Orion.Now() - my_last_msg_time) > 60*60*1000 && msg_counter < 12) {
			if (!init) {// {
				//Mouse moves.
				var mouse_pos = Orion.GetMousePosition();
				//Player moves.
				var player_pos = {'X': Player.X(), 'Y': Player.Y()};
				//Player changes faccets.
				var faccet = Orion.FindObject(backpack).Map();
				
				create_is_player_active_gump();
				
				//Wait till an action indicating player activity occurs.
				while (!Shared.GetVar('player_is_active') && positions_match(mouse_pos, Orion.GetMousePosition()) && (positions_dict_match(player_pos, {'X': Player.X(), 'Y': Player.Y()}) || Orion.IsWalking() || Player.Hidden()) && faccet == Orion.FindObject(backpack).Map() && Shared.GetVar('continue_wc_messaging')) {
					if (Orion.IsWalking() || Player.Hidden()) {
						player_pos = {'X': Player.X(), 'Y': Player.Y()};
					}
					
					Orion.Wait(50);
				}
				
				//If an action occured. Remove the gump.
				if (!Shared.GetVar('player_is_active')) {
					active_player_answered();
				}
				
				havent_checked_counter = 0;
			}
			else {
				havent_checked_counter += 1;
			}
			
			//Launch a wc message since all rules have been followed.
			if ((init || Shared.GetVar('player_is_active')) && Shared.GetVar('continue_wc_messaging')) {
				Orion.Say('[c ' + message);
			}
			
			//Reset message criteria.
			my_last_msg_time = Orion.Now();
			msg_counter += 1;
			other_msgs = [];
			init = false;
		}
		
		//Check for new world chat messages.
		var last_msg_time = Orion.Now()-1000;
		var last_message = Orion.LastJournalMessage();
		var past_message = last_message;
		while (past_message != null && past_message.Timer() > last_msg_time && past_message.Timer() > my_last_msg_time && other_msgs.length < 12 && msg_counter < 12 && Shared.GetVar('continue_wc_messaging')) {
			var text = past_message.Text();
			//Check if the message is a world chat message that wasn't ours.
			if (past_message.Flags() == 2 && has_wc_format(text) && other_msgs.indexOf(text) == -1 && !(Orion.Contains(text, message) && Orion.Contains(text, Player.Name()))) {
				other_msgs.push(text);
			}
			
			//Continue iterating.
			past_message = past_message.PrevMessage();
		}
		
		//If its reset time and we haven't reset, reset.
		if (correct_time(time_difference).slice(0, 4) == '0:00' && !day_change_accounted_for) {
			msg_counter = 0;
			day_change_accounted_for = true;
		}
		else if (correct_time(time_difference).slice(0, 4) == '0:00') {
			day_change_accounted_for = false;
		}
		
		//Wait a little bit of time before checking the messaging criteria.
		while (Orion.InRange(Orion.Now() - (last_msg_time+1000), 0, 800) && Shared.GetVar('continue_wc_messaging')) {
			Orion.Wait(100);
		}
		Orion.Wait(100);
	}
}

function has_wc_format(message) {
	//[00:00] Player Name: message
	return message.length > 11 && message[0] == '[' && message[3] == ':' && message[6] == ']' && Orion.Contains(message, '] ') && Orion.Contains(message, ': ');
}

function positions_match(initial_pos, current_pos) {
	//objects are not null and the X/Ys match.
	return initial_pos && current_pos && initial_pos.X() == current_pos.X() && initial_pos.Y() == current_pos.Y();
}

function positions_dict_match(initial_pos, current_pos) {
	return initial_pos['X'] == current_pos['X'] && initial_pos['Y'] == current_pos['Y'];
}

function create_is_player_active_gump() {
	Shared.AddVar('player_is_active', false);
	
	//Using custom gump 50 as a random number assuming someone doesn't
	//	have a custom gump with the id of 50.
	var gump = Orion.CreateCustomGump(50);
	gump.Clear();
	
	//Simple pop up gump.
	gump.AddText(350, 300, '0x0035', 'Are you online?');
	gump.AddButton(1, 350, 320, '0x00F9', '0x00F7', '0x00F8', 0, 1, 1);
	gump.SetCallback('active_player_answered');
	
	//Make gump visible.
	gump.Update();
}

function active_player_answered() {
	Shared.AddVar('player_is_active', true);
	Orion.CloseGump('custom', 50);
}

function get_shard_time() {
	Orion.Say('[time');
	
	//Look for the time that was asked for just now.
	var start_time = Orion.Now();
	while (!Orion.InJournal('Universal Coordinated Time', 'sys', '0', any, start_time, Orion.Now()))
		Orion.Wait(50);
	
	var message = Orion.InJournal('Universal Coordinated Time', 'sys', '0', any, start_time, Orion.Now());
	return message.Text().split(', ')[1].split(' (')[0];
}

function get_time_difference() {
	//Getting shard time is a failure point. Trying to do this as little as possible
	//	by getting the time and then correcting Orion time to find server time.
	var shard_time = get_shard_time();
	var shard_hour = parseInt(shard_time.split(':')[0]);
	var my_time = Orion.Time('hh:mm:ss');
	var my_hour = parseInt(my_time.split(':')[0]);
	
	return shard_hour - my_hour;
}

function correct_time(time_difference) {
	//Correct Orion time based on a previously found time difference.
	//	this would deviate if the script ran over daylight savings time, but still work.
	//	the reset time would just be an hour off once the time fell or sprung.
	var my_time = Orion.Time('hh:mm:ss');
	var my_hour = my_time.split(':')[0];
	
	var corrected_hour = parseInt(my_hour) + parseInt(time_difference);
	
	if (corrected_hour < 0)
		corrected_hour = 24 + corrected_hour;
	else if (corrected_hour > 24)
		corrected_hour %= 24;
	
	return String(corrected_hour) + ':' + Orion.Time('mm:ss');
}
Notes
This follows the 4 main rules:
  • 12 announcements between 00:00 and 23:59 shard time.
  • 1 hour between 2 announcements.
  • 12 lines of other world chat messages between announcements.
  • Player must be at their keyboard.
You can leave this script running while you are away, as it will check if you are online before posting another announcement. It is meant to be able to run with other scripts and be as self contained as possible.

Extra details and Caveats
If you are walking around or moving your mouse, you will not hardly notice the afk checks. If you leave it and come back, just move the mouse. The script should be resistant to Orion pathfinding and hiding scripts as skill raising can be done afk. The script can be run with any other script, if you pause other scripts, ensure you are not pausing this script.

Orion does not allow for you to see all the messages from the entire day (100 journal line limit), therefore it looks to see that it follows the rules after the script has started without checking what happened before. If you are starting and stopping the script, you are probably breaking spamming rules.

This is not a shard endorsed script, it intends to make rule following easier, but any determined or careless player can always find ways around the guard rails. Good luck, have fun, use responsibly.
Respectfully,
Paroxysmus ILV Master Spellcaster

Image
Post Reply