Scrambling words using 2D array?

Hello!

A while back I stumbled upon this great piece of open source code written by a developer which simulates the feeling of reading with dyslexia: Dsxyliea

(I’ll copy/paste it at the end of this post!)

I’d love to use it in one of my projects. Problem: I know very little about JavaScript, and even less about JQuery. So I’m doing my best to translate what I can in C#, but as somewhat of an advanced beginner I am afraid I’ll need some help!

Here’s what I have so far:

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using UnityEngine.UI;


public class ScrambleWords : MonoBehaviour {

	//public List <string> wordsList;
	//public List <char> lettersList;
	//public List <List <string>> wordsToScrambleList = new List <List <string>>();

	public string[] wordsArray;
	public char[] characters;

	//public string[][] arrayOfScrambledLetters;
	public Text theTextToScramble;

	public bool runItOnlyOnceForTheMoment = false;


	void Start () {

		theTextToScramble.text = "This wonderful text is only temporary and helps me test the script for scrambling words.";
	}


	void Update () {

		if (!runItOnlyOnceForTheMoment) {
			runItOnlyOnceForTheMoment = true;
			MessingWithWords();
		}
	}


	public void MessingWithWords () {


		//SPLIT SENTENCE INTO WORDS ; CHAR [0] = WHITESPACE
		wordsArray = theTextToScramble.text.Split(new char[0]);


		for (int i = 0; i < wordsArray.Length; i++) {

			//SPLIT EACH WORD INTO CHARS AND PUT EACH OF THE CHARS IN THEIR OWN LISTS
			characters = wordsArray*.ToCharArray();*
  •  	//IF THe WORD IN THREE OR LESS CHARS LONG, DON'T CONTINUE*
    

_ if (wordsArray*.Length <= 3) {_
_
return;_
_
}*_

* for (int y = 0; y < characters.Length; y++) {*

* Debug.Log(“Inside second loop. Here are some chars:” + characters[y]);*

* //MESS UP THE INDEX OF THOSE CHARS.*
//Does not work ---->
characters[y] = characters[Random.Range(1, characters.Length - 1)];
* //OPTIONAL: ONLY LIMIT TO ONE CHARACTER CHANGE?*

* //OPTIONAL: DO NOT CHANGE FIRST (0) AND LAST INDEX (Index.Length - 1)*
* }*

* }*

* //PUT THE CHARS BACK INTO THE ORIGINAL LIST OF WORDS*

* //PRINT THE NEW SENTENCE! DO I ACTUALLY NEED THIS LINE?*

* //REPEAT THE WHOLE PROCESS EVERY HALF SECOND OR SO*

* Debug.Log (“End of update.”);*

* }*
}
The first issue that I ran in: it seems that the for loop only goes through the first three words. When I don’t set it to run only once, this is what I have in the Console window:
[83190-debug1.png|83190]_
_
[83191-debug2.png*|83191]*
_*
_*
It seems like it repeats the process for the first few words and seems “stuck” on the fourth (which appears under Characters in the Inspector).
The second issue that I am wondering about is the use of two arrays when perhaps a 2D array would be better to use. I tried a little bit writing with one but none of my solutions worked…
Oh and also how to actually scramble to words! I thought messing up with the index for each chars would do something but the text remains pristine.
Geon’s code for reference:



  1. \d ↩︎

Hi @Fahryem,

I found it very interesting as well and so I finished to convert your class by looking at the javascript.

There is no need to use a 2D array in this current stage. Geon is using that because at every processing (the half second you spotted) he actually reads a set of sentences and the process all of then he changes only 0.1 of them.

I am not sure why you get the error, but definitely this is not a swapping:

characters[y] = characters[Random.Range(1, characters.Length - 1)];

and you end up having words that are formed with just a subset of the original characters.

I am using Array.Copy to create a sub array for processing only the central characters of the word. It requires you to import System (add using System; on top of your script) and change the Random static class calls like following:

UnityEngine.Random.Range(0, messpart.Length);

Here is the major part that I have changed. I created a MessyUpPart function to mirror what he has done

    void Update()
    {

        if (!runItOnlyOnceForTheMoment)
        {
            runItOnlyOnceForTheMoment = true;
            MessingWithWords();
        }
    }


    private void MessyUpPart(ref char[] messpart)
    {
        //index from where pick char to exchange
        int a = 0, b = 0;
        //to make sure we switch one from the bottom towards the front part of the word
        while (!(a < b))
        {
            a = UnityEngine.Random.Range(0, messpart.Length);
            b = UnityEngine.Random.Range(0, messpart.Length);
        }

        char temp = messpart[a];
        messpart[a] = messpart**;**

messpart = temp;
}

public void MessingWithWords()
{

//SPLIT SENTENCE INTO WORDS ; CHAR [0] = WHITESPACE
wordsArray = theTextToScramble.text.Split(new char[0]);

for (int i = 0; i < wordsArray.Length; i++)
{

//SPLIT EACH WORD INTO CHARS AND PUT EACH OF THE CHARS IN THEIR OWN LISTS
characters = wordsArray*.ToCharArray();*

//IF THe WORD IN THREE OR LESS CHARS LONG, DON’T CONTINUE
if (wordsArray*.Length <= 3)*
{
//Instead of breaking let’s see the other words
continue;
}

//OPTIONAL: DO NOT CHANGE FIRST (0) AND LAST INDEX (Index.Length - 1)
char[] subcharacters = new char[characters.Length - 2];
Array.Copy(characters, 1, subcharacters, 0, subcharacters.Length);

//OPTIONAL: ONLY LIMIT TO ONE CHARACTER CHANGE?
//MESS UP THE INDEX OF THOSE CHARS.
MessyUpPart(ref subcharacters);

//PUT THE CHARS BACK INTO THE WORD
Array.Copy(subcharacters, 0, characters, 1, subcharacters.Length);

//PUT THE CHARS BACK INTO THE ORIGINAL LIST OF WORDS
wordsArray = new string(characters);

}

//PRINT THE NEW SENTENCE! DO I ACTUALLY NEED THIS LINE?
//reconstructing the sentence as string, checking wordsarray lenght is != 0 just to make sure
string debugstring = wordsArray.Length != 0 ? wordsArray[0] : “” ;
for (int i = 1; i < wordsArray.Length; i++)
{
debugstring += " " + wordsArray*;*
}

//REPEAT THE WHOLE PROCESS EVERY HALF SECOND OR SO
//(this you do in the update function)
Debug.Log(debugstring);

}
If you have any more questions let me know.