Official site anti-cheat Ultra Core Protector

Home Download F.A.Q. Addons Monitor Forum Support Advertise English version site UCP Anti-Cheat  Russian version site UCP Anti-Cheat
Ultra Core Protector - is the client-server anti-cheat freeware, for server protection from unscrupulous players.

Abilities Supported games  
Half-Life
Condition Zero
Counter-Strike 1.6
Day of Defeat
Adrenaline Gamer
Team Fortress Classic
Counter-Strike Source
MU Online
Ragnarok Online
Half-Life 2 Deathmatch
Adrenaline Gamer 2
Team Fortress 2
CSGO: Nice alternative for W2S for read-only aim hacks

Good day!

As this is my first post here, and do not wish to look like a leech just trying to get some help.
That’s why I’ll start this off by providing something to the community first before crying for help

I’m a very dedicated programmer, and have always been one – starting at the age of 12.
I absolutely love “re-inventing the wheel” and do everything on my own – use of libraries? Meh!
Yes, I even made my own programming language – that’s how hipster I am.
No, I don’t want to just boast, I want to transport that I am not just someone who wants to hack in games.
I’m a person who LOVES the subject and does it SOLELY for self-enhancement and experience.
That’s something important for me, you can see it as introduction.

Sorry – now to the Topic:

I am currently working on a multihack for CS:GO written in C# (yes, I know, native C/C++ = god tier) called “Project:Matchlock”.
When I wanted to implement the aim assist module, I crossed a problem many have faced before: W2S.
What I saw was that I do not want to read into that stuff as I did not want to calculate in stuff like FOV etc. (I might in fact have been too lazy at that point)
Writing the viewAngles into memory is something that hurts my feelings a little bit, too.

So I had and idea, that (from my perspective) completely eliminates the need for W2S in that use case – please correct me if I’m wrong.
The solution I came up with can even be used for a lot more than just an aim lock/assist, as you’ll see below.
This is unlikely to be something ‘new’ and ‘genius’, but I had the idea myself please let me be proud just for a second.
Note: The user ‘zniv’ has already posted a similar article with a about the same idea,
but a completely different approach (from what I could tell) – so please give this one a chance,
too. It is also WAY simpler (as in easy-to-comprehend) than all other attempts I’ve seen yet.

So, what’s our problem?
We want to (realistically) aim at a target’s head with absolute basic information and no writing into memory.

What do we have?
List of entities, their (bone) positions and the player’s viewAngles.
Oh, and mouse_event();

This is what I came up with:
(Please note that this is not a tutorial, just a technique – NO fully copy-pastable code.
I use implicit self-explanatory classes and functions that someone who is coding hacks should understand without any further explanation.
I am aware what OOP is, every bad code style was solely used for better display of what is happening.
If something should really be unclear, please tell me and I’ll fix it.)

// just some config vars
SEEK_MODE seekMode = SEEK_MODE.DistanceToCrosshair;
float variation = 0.16f;
float velocity = 7.2f;
float flickImpulse = 16.4f;
float maxScanAngle = 32f;
bool forceWallbang = false;

// the aim assist tick function, basically a do {} while
void step() {
Player player = Player.read();
Entity target = null;
float lowest = 360f;
for (int i = 0; i < entityCount; i++) { Entity e = Entity.read(i); if (e == null || e.health == 0 || e.teamId == player.teamId || e.dormant) continue; if (seekMode == SEEK_MODE.DistanceToCrosshair) { // get the angle between the vectors (vecOrigin + vecViewOffset of the player and headBone position of the entity) Angle angle = getVectorAngle(player.headNode, e.headNode); // don't aim at people behind you, that'd look very weird. so we continue if the target is too far away from our crosshair if (angle > maxScanAngle) continue;

// check if the angular distance is smaller than the smallest one within the current loop
float dist = getAngularDistance(player.viewAngles, angle);
if (dist < lowest) { target = e; lowest = dist; } } else if (...) { ... } } if (target != null) { // now we're getting the mouse movement needed using getMouseDrag (defined below) Vector mouseDelta = getMouseDrag(player.headNode, entity.headNode, velocity, flickImpulse); // using the amount of mouse movement (less than ~.5f is about on target) we decide what we do next float amount = mouseDelta.magnitude(); if (amount < .5f) { if (forceWallbang) trigger(); // this will alway shoot at the target, no matter if visibile or not else { // basically a small trigger bot to survive at least 2 matches without overwatch ban Entity e = Entity.getFromCrosshairId(); if (e == null || e.health == 0 || e.teamId == player.teamId || e.dormant) return; else trigger(); } } else { // do relative/additive mouse movement using the event code 0x1 // x and y are reversed because x is yaw and y is pitch in screen dimensions // y is also inverted because it somehow gets reversed on the way here mouse_event(0x1, -mouseDelta.y, mouseDelta.x, 0, 0); } } } // calculate a relative Vector that describes mouse movement using some config parameters // -> this is where it gets interesting <- and my actual idea is at Vector getMouseDrag(Angle from, Angle to, float velocity, float flick) { // first, get the delta (difference) between the angles Angle delta = new Angle(from.x - to.x, from.y - to.y); // normalize the angles. // this a super important step, as it will prevent you from turning 350 degrees right - // when actually trying to aim at a target that is 10° left of you. trigonometry, yea. delta.x = normalizeAngle(delta.x); delta.y = normalizeAngle(delta.x); // now normalize the angle itself to get an angle we can multiply the velocity with int xp = (delta.x < 0 ? -1 : 1), // xp stands for "xPolarity" here yp = (delta.y < 0 ? -1 : 1); // if one axis has a very low absolute delta, we ignore the polarity entirely if (abs(delta.x) < .1f) xp = 0; if (abs(delta.y) < .1f) yp = 0; // create a new, normalized angle // note that this is not the same as "power of 1" vector that results in a magnitude of 1. // this is because diagonal movements SHOULD be 'faster' here and thus have higher magnitude Angle normalized; if (delta.x < delta.y) { normalized = new Angle(xp * abs(delta.x / delta.y), yp); } else { normalized = new Angle(xp, yp * abs(delta.y / delta.x)); } // calculate the actual mouse movement values, this is just some random formula, there's better possibilities yes. float mx = (normalized.x * velocity) + ((delta.magnitude() / velocity) * flick), my = (normalized.x * velocity) + ((delta.magnitude() / velocity) * flick); // return that shit! return new Vector(mx, my); } float normalizeAngle(float angle) { do { if (angle < -180) angle = 360 + angle; else if (angle > 180) angle = -360 + angle;
} while (angle < -180 || angle > 180); // cs:go does not go 0 to 360°, but rather -180 to 180°.
return angle;
}

Angle getAngularDistance(Angle from, Angle to) {
Angle delta = new Angle(from.x - to.x, from.y - to.y);
return delta.magnitude(); // magnitude is the length of C (in a triangle example) basically pythagoras (= sqrt(a*a + b*b))
}

Angle getVectorAngle(Vector from, Vector to) {
return ...; // this would just overload this post, i think we all know what this does.
}

This works VERY well, even if it looks weird at first.
The finished version of course does a lot more, with over 40 configuration settings such as “keep initial target until button released” or “force wallbangs”

Thinking further, I saw that I could also implement recoil reduction in the same manner:
All I had to do, is add the aimPunchAngle to my target angle and voila: Now we never have to move our hands at all anymore.

// we're inside the step function as seen in the above code block
...
if (target != null) {
Vector mouseDelta = getMouseDrag(player.headNode, entity.headNode, velocity, flickImpulse);

mouseDelta.x -= player.aimPunchAngle.x * 2f; // there's a reason for why you have to multiply the punchAngle by 2.
// someone on this board explained that a while ago but i forgot the exact reason.
mouseDelta.y -= player.aimPunchAngle.y * 2f;

float amount = mouseDelta.magnitude();
...
}
...

I’m currently working on the humanization of this thing, because it still has way too much of a “machine” feeling.
What I tried was letting each shot land on randomized spots around the target – but this looked absolutely alien.
I’ll be more than happy about any suggestions, feedback or criticism!

I really hope I contributed something with this post, I’m sorry for writing such truck loads.

Wish you all happy hacking out there!