Elin:Code Analysis/Fishing: Difference between revisions

From Ylvapedia
m (Fix small fishing spoiler format.)
(Added fishing sea land feat.)
Line 98: Line 98:
The initial chance of catching one extra fish starts at '''5%'''.
The initial chance of catching one extra fish starts at '''5%'''.


If the land feats include '''Beach (3604)''' and '''Fishing Spot (3706)''', these feats will contribute additional chances to the base chance.
If the land feats include:
* '''Beach (3604)''': Adds '''20%''' to the base chance.
* '''Sea (3605)''': Adds '''20%''' to the base chance.
* '''Fishing Spot (3706)''': Adds '''25%''' to the base chance.


For example:
Since only '''Sea (3605)''' or '''Beach (3604)''' can be present at the same time (not both), the total chance is calculated as:
* '''Beach (3604)''' adds '''20%''' to the base chance.
* '''Fishing Spot (3706)''' adds '''25%''' to the base chance.
 
Starting with a '''5% chance''', the total chance is calculated using the following code:


<pre>
<pre>
chanceForOneMoreFish = 5
chanceForOneMoreFish = 5
chanceForOneMoreFish += isBeach * 20 + isFishingSpot * 25
chanceForOneMoreFish += isBeach * 20 + isSea * 20 + isFishingSpot * 25
</pre>
</pre>


Where:
Where:
* '''isBeach''' is a flag (either 0 or 1) indicating whether the land feat is a '''Beach (3604)'''.
* '''isBeach''': A flag (either 0 or 1) indicating whether the land feat is a '''Beach (3604)'''.
* '''isFishingSpot''' is a flag (either 0 or 1) indicating whether the land feat is a '''Fishing Spot (3706)'''.
* '''isSea''': A flag (either 0 or 1) indicating whether the land feat is '''Sea (3605)'''.
 
* '''isFishingSpot''': A flag (either 0 or 1) indicating whether the land feat is a '''Fishing Spot (3706)'''.
If both features are present (i.e., both flags are set to 1), then:


For example:
* If '''Sea (3605)''' is present, and '''Fishing Spot (3706)''' is also present:
<pre>
chanceForOneMoreFish = 5 + 1 * 20 + 1 * 25 = 50
</pre>
* If '''Beach (3604)''' is present instead of '''Sea (3605)''':
<pre>
<pre>
chanceForOneMoreFish = 5 + 1 * 20 + 1 * 25 = 50
chanceForOneMoreFish = 5 + 1 * 20 + 1 * 25 = 50
Line 123: Line 127:
==== Checking the Chance to Increase the Number of Fish ====
==== Checking the Chance to Increase the Number of Fish ====


The '''chanceForOneMoreFish''' value is then compared to a random number generated by the <code>rnd(100)</code> function. The value of <code>rnd(100)</code> generates a random number between '''0''' and '''99''' (inclusive).
The '''chanceForOneMoreFish''' value is compared to a random number generated by the <code>rnd(100)</code> function, which produces a number between '''0''' and '''99''' (inclusive).


If the value of '''chanceForOneMoreFish''' is greater than or equal to the random number, the number of fish will increase by '''1'''.
If '''chanceForOneMoreFish''' is greater than or equal to the random number, the number of fish will increase by '''1'''.


This check is done with:
This check is implemented with:


<pre>
<pre>
Line 133: Line 137:
</pre>
</pre>


* If the random number generated by <code>rnd(100)</code> is '''50 or less''', the number of fish will increase by '''1'''.
For example:
* If the random number is '''greater than 50''', the number of fish will remain the same.
* If '''chanceForOneMoreFish = 50''', and the random number generated by <code>rnd(100)</code> is '''50 or less''', you will catch an additional fish.


Thus, the probability of increasing the number of fish is '''50%''' (because '''chanceForOneMoreFish = 50''' ).
==== Example with Land Feats ====


==== Example with Land Feats ====
===== Example 1: Fishing Spot (3706) and Sea (3605) =====


Let's say your fishing level is '''22''', and the fish LV is '''1'''. You calculate the base number of fish as:
Let's say your fishing level is '''22''', and the fish LV is '''1'''. The base number of fish is calculated as:


<pre>numberOfFish = rnd(22 / (1 + 10)) + 1 = rnd(2) + 1</pre>
<pre>
numberOfFish = rnd(22 / (1 + 10)) + 1 = rnd(2) + 1
</pre>


Thus, you could catch '''1 or 2 fish''', based on the random result.
This gives '''1 or 2 fish''', depending on the random result.


Now, you evaluate the land feats:
Now, evaluating the land feats:
* Starting with '''chanceForOneMoreFish = 5''' (the base chance).
* Start with '''chanceForOneMoreFish = 5''' (base chance).
* If the land feats are present:
* '''Sea (3605)''' adds '''20'''.
** '''Beach (3604)''' adds '''20''' to '''chanceForOneMoreFish'''.
* '''Fishing Spot (3706)''' adds '''25'''.
** '''Fishing Spot (3706)''' adds '''25''' to '''chanceForOneMoreFish'''.


So, the new '''chanceForOneMoreFish''' becomes:
The new '''chanceForOneMoreFish''' becomes:


<pre>
<pre>
Line 160: Line 165:
Next, the random chance is checked:
Next, the random chance is checked:


<pre>if (chanceForOneMoreFish >= rnd(100))</pre>
<pre>
if (chanceForOneMoreFish >= rnd(100))
</pre>
 
If the random number generated by <code>rnd(100)</code> is '''50 or less''', the number of fish will increase by '''1'''. Thus:
* '''numberOfFish = numberOfFish + 1''' (if the random check passes).
* If the random number exceeds '''50''', the number of fish remains unchanged.


If the random number generated by <code>rnd(100)</code> is '''50 or less''', '''numberOfFish''' will increase by 1. This means that if the random number is between '''0 and 50''' (inclusive), you will catch an additional fish, making '''numberOfFish''' increase by 1.
===== Example 2: Fishing Spot (3706) and Beach (3604) =====


So, '''numberOfFish''' is increased by '''1''' based on land feats, making it:
For the same fishing level and fish LV, the land feats contribute:
* '''Beach (3604)''' adds '''20'''.
* '''Fishing Spot (3706)''' adds '''25'''.


* '''numberOfFish = numberOfFish + 1''' (if the random check passes).
The total '''chanceForOneMoreFish''' remains:
* If the random number exceeds '''50''', '''numberOfFish''' remains the same.
 
<pre>
chanceForOneMoreFish = 5 + 20 + 25 = 50
</pre>
 
The random check behaves the same as above, with the same chance for an additional fish.


====Number of Fish Table====
====Number of Fish Table====
Line 194: Line 212:
|}
|}


====Code (EA 23.37)====
==== Code (EA 23.40) ====


<syntaxhighlight lang="c#" line="1">
<syntaxhighlight lang="c#" line="1">
Line 201: Line 219:
if (EClass.Branch != null)
if (EClass.Branch != null)
{
{
     num4 += EClass.Branch.Evalue(3604) * 20 + EClass.Branch.Evalue(3706) * 25;
     num4 += EClass.Branch.Evalue(3604) * 20 + EClass.Branch.Evalue(3605) * 20 + EClass.Branch.Evalue(3706) * 25;
}
}
if (num4 >= EClass.rnd(100))
if (num4 >= EClass.rnd(100))

Revision as of 10:15, 26 November 2024

Calculations

Fish LV

The formula to calculate the fish LV that can be caught based on your fishing level:

fishLV = rnd(fishingLevel * 2) + 1
  • fishingLevel: Your current fishing skill level.
  • rnd: A random number between 0 and the value passed into the function.

Example

If your fishing level is 3, the potential fish LV is calculated as:

rnd(3 * 2) + 1

This gives a range of 1 to 6, meaning you can catch fish with LV between 1 and 6.

Fish LV Range Table

Fishing Level Minimum LV Maximum LV
1 1 2
2 1 4
3 1 6
4 1 8
5 1 10
6 1 12
7 1 14
8 1 16
9 1 18
10 1 20
11 1 22
12 1 24
13 1 26
14 1 28
15 1 30
16 1 32
17 1 34
18 1 36
19 1 38
20 1 40

Code (EA 23.37)

int num3 = EClass.rnd(num * 2) + 1;
thing = ThingGen.Create("fish", -1, num3);

Number of Fish

The formula to calculate the number of fish you can catch based on your fishing level:

numberOfFish = rnd(fishingLevel / (fishLV + 10)) + 1
  • fishingLevel: Your current fishing skill level.
  • fishLV: The fish LV.
  • rnd: A random number between 0 and the value passed into the function.

Example

If your fishing level is 22, and the fish LV is determined to be 1, the potential number of fish is calculated as:

rnd(22 / (1 + 10)) + 1

This simplifies to:

rnd(22 / 11) + 1

The rnd(2) generates a random number between 0 and 1. Adding 1 ensures that you will catch at least 1 fish, and the number of fish can either be 1 or 2, depending on the random result.

Adding Land Feats

The initial chance of catching one extra fish starts at 5%.

If the land feats include:

  • Beach (3604): Adds 20% to the base chance.
  • Sea (3605): Adds 20% to the base chance.
  • Fishing Spot (3706): Adds 25% to the base chance.

Since only Sea (3605) or Beach (3604) can be present at the same time (not both), the total chance is calculated as:

chanceForOneMoreFish = 5
chanceForOneMoreFish += isBeach * 20 + isSea * 20 + isFishingSpot * 25

Where:

  • isBeach: A flag (either 0 or 1) indicating whether the land feat is a Beach (3604).
  • isSea: A flag (either 0 or 1) indicating whether the land feat is Sea (3605).
  • isFishingSpot: A flag (either 0 or 1) indicating whether the land feat is a Fishing Spot (3706).

For example:

  • If Sea (3605) is present, and Fishing Spot (3706) is also present:
chanceForOneMoreFish = 5 + 1 * 20 + 1 * 25 = 50
  • If Beach (3604) is present instead of Sea (3605):
chanceForOneMoreFish = 5 + 1 * 20 + 1 * 25 = 50

Checking the Chance to Increase the Number of Fish

The chanceForOneMoreFish value is compared to a random number generated by the rnd(100) function, which produces a number between 0 and 99 (inclusive).

If chanceForOneMoreFish is greater than or equal to the random number, the number of fish will increase by 1.

This check is implemented with:

if (chanceForOneMoreFish >= rnd(100))

For example:

  • If chanceForOneMoreFish = 50, and the random number generated by rnd(100) is 50 or less, you will catch an additional fish.

Example with Land Feats

Example 1: Fishing Spot (3706) and Sea (3605)

Let's say your fishing level is 22, and the fish LV is 1. The base number of fish is calculated as:

numberOfFish = rnd(22 / (1 + 10)) + 1 = rnd(2) + 1

This gives 1 or 2 fish, depending on the random result.

Now, evaluating the land feats:

  • Start with chanceForOneMoreFish = 5 (base chance).
  • Sea (3605) adds 20.
  • Fishing Spot (3706) adds 25.

The new chanceForOneMoreFish becomes:

chanceForOneMoreFish = 5 + 20 + 25 = 50

Next, the random chance is checked:

if (chanceForOneMoreFish >= rnd(100))

If the random number generated by rnd(100) is 50 or less, the number of fish will increase by 1. Thus:

  • numberOfFish = numberOfFish + 1 (if the random check passes).
  • If the random number exceeds 50, the number of fish remains unchanged.
Example 2: Fishing Spot (3706) and Beach (3604)

For the same fishing level and fish LV, the land feats contribute:

  • Beach (3604) adds 20.
  • Fishing Spot (3706) adds 25.

The total chanceForOneMoreFish remains:

chanceForOneMoreFish = 5 + 20 + 25 = 50

The random check behaves the same as above, with the same chance for an additional fish.

Number of Fish Table

Fish LV Minimum Fishing Level for 2 Fish Minimum Fishing Level for 3 Fish
1 22 33
5 30 45
10 40 60
15 50 75
20 60 90
25 70 105
30 80 120
35 90 135
40 100 150

Code (EA 23.40)

num2 = EClass.rnd(num / (num3 + 10)) + 1;
int num4 = 5;
if (EClass.Branch != null)
{
    num4 += EClass.Branch.Evalue(3604) * 20 + EClass.Branch.Evalue(3605) * 20 + EClass.Branch.Evalue(3706) * 25;
}
if (num4 >= EClass.rnd(100))
{
    num2++;
}
if (thing != null)
{
    thing.SetNum(num2);
    thing.SetBlessedState(BlessedState.Normal);
}

Fishing Speed

The fishing process involves two key variables:

  • progress: Represents the overall duration or percentage of fishing completion, ranging from 0 to 100.
  • hit: Tracks the number of attempts made during the fishing fight. The following conditions apply:
    • Increase: hit increments on each attempt until either:
      • The fish is caught (when hit > random threshold).
      • Certain random conditions reset hit to 0.

Success

The formula to calculate the success threshold for catching a fish is:

successThreshold = Mathf.Clamp(10 - rnd(fishingLevel + 1) / 10, 5, 10)
  • fishingLevel: Your current fishing skill level.
  • rnd: A random number between 0 and the value passed into the function.
  • Clamp: Ensures the value stays between 5 (easiest) and 10 (hardest).

The actual success logic occurs as follows:

if (hit > rnd(successThreshold)) {
    hit = 100;
    progress = MaxProgress;
}
  • hit: Tracks the current number of attempts. The fish is caught if hit exceeds the random roll of the successThreshold.
  • progress: Automatically completes when success occurs.

Example

If your fishing level is 20, the calculation proceeds as follows:

  1. rnd(20 + 1) generates a random number between 0 and 20.
  2. This random number is divided by 10 and subtracted from 10.
  3. The result is clamped to the range [5, 10], determining the successThreshold.

For example:

  • If rnd(21) = 10, the calculation is:
successThreshold = Mathf.Clamp(10 - (10 / 10), 5, 10) = 9

A random roll of rnd(9) determines the threshold. If hit > rnd(9), the fish is caught.

Success Threshold Table

Fishing Level Min successThreshold Max successThreshold
1 10 10
5 10 10
10 9 10
15 9 10
20 8 10
25 8 10
30 7 10
35 7 10
40 6 10
45 6 10
50 5 10
55 5 10
60 5 10

Reset

The formula to determine whether hit resets is:

resetThreshold = Mathf.Clamp(10 - rnd(fishingLevel + 1) / 5, 2, 10)
  • fishingLevel: Your current fishing skill level.
  • rnd: A random number between 0 and the value passed into the function.
  • Clamp: Ensures the value stays between 2 (easiest threshold to reset) and 10 (hardest threshold to reset).

If rnd(resetThreshold) equals 0, and progress >= 10, the hit counter resets to 0.

Example

If your fishing level is 30, the calculation proceeds as follows:

  1. rnd(30 + 1) generates a random number between 0 and 30.
  2. This random number is divided by 5 and subtracted from 10.
  3. The result is clamped to the range [2, 10], determining the resetThreshold.

For example:

  • If rnd(31) = 10, the calculation is:
resetThreshold = Mathf.Clamp(10 - (10 / 5), 2, 10) = 8

A second random roll, rnd(8), is performed. If the result is 0, the hit counter resets.

Reset Threshold Table

Fishing Level Min resetThreshold Max resetThreshold
1 10 10
5 9 10
10 8 10
15 7 10
20 6 10
25 5 10
30 4 10
35 3 10
40 2 10
45 2 10
50 2 10

Code (EA 23.37)

public override void OnProgress()
{
	if (this.owner.IsPC && (this.owner.Tool == null || !this.owner.Tool.HasElement(245, 1)))
	{
		this.Cancel();
		return;
	}
	if (this.hit >= 0)
	{
		this.owner.renderer.PlayAnime(AnimeID.Fishing, default(Vector3), false);
		this.owner.PlaySound("fish_fight", 1f, true);
		this.Ripple();
		int a = Mathf.Clamp(10 - EClass.rnd(this.owner.Evalue(245) + 1) / 10, 5, 10);
		if (this.hit > EClass.rnd(a))
		{
			this.hit = 100;
			this.progress = this.MaxProgress;
		}
		this.hit++;
		return;
	}
	if (EClass.rnd(Mathf.Clamp(10 - EClass.rnd(this.owner.Evalue(245) + 1) / 5, 2, 10)) == 0 && this.progress >= 10)
	{
		this.hit = 0;
	}
	if (this.progress == 2 || (this.progress >= 8 && this.progress % 6 == 0 && EClass.rnd(3) == 0))
	{
		this.owner.renderer.PlayAnime(AnimeID.Shiver, default(Vector3), false);
		this.Ripple();
	}
}