2012-10-25

Eclipse Juno problem building Android NDK

When building code from the Android NDK Beginners Guide, simply trying to get a tutorial on OpenSL to run, I ran into some freaky and troublesome bugs with Eclipse.

Code from Chapters 1-5 built without a hitch.  Starting with Chap. 6,  I started having strange intermittent problems. I could import a project, build it and run it, but then I'd do a double take when errors started popping up all over the place, without having made any changes.

I was getting "Field could not be resolved" and "Function could not be resolved" under the Problems tab whenever I tried to build the project.  If I build from the command line, I can get the project to "Run as Android Project" even right inside Eclipse, however, as soon as I open a file for editing, little red error X's start popping up all over everything.  I spent hours and hours trying to check paths and properties, and project configuration, and even my .bashrc and .profile files.  ANYTHING to hunt down and fix this.

Finally, I went to Project/Properties/C-C++ General/Code Analysis and un-checked a couple boxes:
Field could not be resolved
Function could not be resolved


NOT an ideal solution, because now I won't get nice error highlighting for miss-spelled function names etc... BUT now it works inside Eclipse.  This can be set on either a Workspace or Project level, by the way.

Apparently the issue is with the Indexer.  The Eclipse Juno Indexer has a bug where in some situations it will give erroneous validation.  This, in turn, log-jams the build/run process, stopping it in it's tracks based on imaginary errors.  Another way to get around it is to simply right-click on the errors in the "Problems" Tab at the bottom of Eclipse, and delete them.

I'll be doing some updates to see if this bug has already been addressed, I hope so.

2012-10-18

Android NDK R7 major issue glDrawTexfOES

Howdy peoples.  Been a minute since I last posted.

In the process of learning the Android NDK, I've run into a potentially immensely frustrating issue, especially for anyone just trying to learn.  This problem had me stumped literally for days.  Until I brought it to my brother's attention and he found this post:

https://groups.google.com/forum/?fromgroups=#!topic/android-ndk/Inip9SFiRZs

I was attempting to build and run, in Eclipse, some tutorial code from the Android NDK Beginners Guide.  Chapters 6 and 7 to be exact.  I started receiving errors like this:


Function 'glDrawTexfOES' could not be resolved

All of the errors were acting as if the libraries simply were not there, but they were there and the make files appeared to all be in order.

Apparently, the issue mentioned in the Google groups post above, extends to the usage of ANY extension libraries post R6.

Currently, my code is building and running after I changed the Android.mk file to include this line:

LOCAL_CFLAGS    := -DRAPIDXML_NO_EXCEPTIONS -DGL_GLEXT_PROTOTYPES

instead of:
LOCAL_CFLAGS    := -DRAPIDXML_NO_EXCEPTIONS

I may come back and post more about this later, because I may want to add more specifics about the errors I received before the fix.

I want to make one thing clear.  Although Eclipse certainly was not helpful in pinpointing the route of this problem, this is not and Eclipse issue, but an Android NDK issue.

UPDATE:
2012/11/06  -- I thought I might as well post this, because it goes right along with the above problem.  I created a short set of instructions for things that need to be done every time I import the tutorial code from the Android NDK Beginner's Guide.  I really don't have time to explain all the reasons why, but I made this list for myself, so I wouldn't forget, and here it is for the public:


Select File/Import
Select the project folder and check the box for copy project to workspace

Open Android.mk, under jni folder, and change this line:

LOCAL_CFLAGS    := -DRAPIDXML_NO_EXCEPTIONS

to this line:

LOCAL_CFLAGS    := -DRAPIDXML_NO_EXCEPTIONS -DGL_GLEXT_PROTOTYPES

Right click on the project and select Android Tools/Fix Project Properties

Then go to project/properties/C/C++ General/code analysis and uncheck:

Field could not be resolved
Function could not be resolved

Or errors will start popping up as soon as you open anything in the editor.  It might run the first time, but as soon as you try to look at it, it will activate the indexer and start throwing up errors.  Apparently the indexer is not designed to recognize NDK code, of some kinds, in an Android development context.  Oh, Eclipse you rascally rabbit you....


2012-09-07

Some thoughts on my philosophy concerning forums


Yeah, this is the editorial section.  Gotta go there some times.

There are far too many forum "gurus" and trolls who have an absolutely TERRIBLE attitude and it shows in the way that they "answer" forum inquiries.  You all know what I am talking about.  Short smart ass replies that say something like, "if you read the documentation...insert annoying tone and useless high level jargon, indecipherable to anyone who doesn't ALREADY know the answer to the posed question bla bla stop bothering me...".  Yes, we all now that guy.  Lots of those guys.

Here is a simple parallel metaphor to explain my philosophy on documentation and the attitude everyone should have if they participate in any capacity in forums:

You can only ever see a movie, for the first time, once. That is why the director has groups come in and view the movie before he puts it out, so that he can get a perspective on how it actually plays to fresh minds, as opposed to the inevitably warped version that will reach his mind after being filtered through all of his knowledge of what he wants the film to be and of what he already has seen countless times while editing. For film directors, this struggle to make something fresh and digestible, even though it is many years old to themselves, is right in front of them at all times. It is obvious. Once you know everything it is difficult to understand what is the needed amount of information to keep the viewer in touch with the narrative of the story and, for instance, what is going on in the heads of the characters at any given moment.  Is this amount enough?  Or am I making assumptions based on my overall knowledge of the complete character including aspects that have not yet been revealed.  A GOOD director is constantly worried about making sure that his message is getting across right now to people BRAND NEW to his story.  Not so much for programmers and IT guys. What do they care about noobs? Noobs should study more, right?

 I disagree. Study is what you do AFTER you are presented with a concept, in order to make it stick in your mind. It is still the job of the teacher, or the documentation, to present that concept clearly and unmistakably and taking into account all the common pitfalls. There is plenty enough gold to be had after the student has been lead to the mine, provided with a pick, and taught how to use it. Uh oh mixed metaphor!

It is wise to always remember that what appears easy to you, may have been easy for you simply because you got lucky enough to come at it from an advantageous angle, or because you had a good teacher, or because you got lucky and did it right the first time, while others may be struggling with shaking off terribly explained paradigms from the last intolerant asshole forum guru that gave them bad "advice" by giving them incomplete information.  If you get lost on the way to going somewhere every time you go there and all of the directions you ask for are wrong, then it is likely you will not remember exactly how to get back there the next time you try again.  Too many confusing memories.

So, if you are a forum guru, your abrupt, short, impatient answers may actually be helping to create more confusion, instead of helping, and guess what, it will come back to haunt you in the form of more "stupid" questions.  Yup, there is a good chance that you, or some other cocky, incomplete answer giver in a related thread, are the entire reason why this questioner is so stumped to begin with.  So just answer the stupid questions already.  Frankly, I see more stupid answers than stupid questions.  You cannot assume that someone is lazy just because they ask a question.  Sometimes frustration and overload make simple, basic concepts slip through the cracks.  Sometimes, dealing with a steady stream of flippant asshole forum "gurus" will just plain unbalance the chemical balance in one's brain!  However, from the answer side, if you KNOW the answer and you just flip a tidbit at them without clearly explaining, then you are truly giving a stupid answer.  If you are picturing yourself as Mr. Miyagi, and think that you are somehow imparting wisdom by being mysterious, then you are, again, an idiot.  You are not in an intense training montage from a Hong Kong kung-fu movie, you are answering a technical question in a forum specifically dedicated to that discipline.

Smart answers give clear concise information.  You knew that when you answered questions in school, right?  So what is the problem?  Real people not good enough for your A-game answers?  It baffles me.  Posting something like "I think it is clearly spelled out in the documentation", is a waste of every one's time.  It is the equivalent of answering a school test question with "that is defined quite well in the dictionary".  Imagine actually putting that on a test.  You would obviously get an "F" for that answer.  I am giving you an "F" right now for your incomplete, and/or smug, answer in the forums.  Put up or shut up.

The future belongs to the noobs!    They can be your allies, or your enemies.  You decide.  If you don't believe that it is safe to assume that anyone who is asking a question is trying to learn, then you should not be answering questions in a forum.  Go code by yourself in the dark and play some more WoW.

Cheers!

ultramanjones

2012-09-06

Property Animation in QML

It has been a long time since I put up a post, I'll try to post more often.  I'm posting up some code I wrote to make a button pulse after clicked and then quit pulsing when clicked again.  Simple, but it contains some important examples of syntax and implementation.  I hope somebody finds it useful.  
Start up QtCreator and select File/New File or Project.../Applications/QtQuick Application (Built-in Elements).  Enter a name and then select only Desktop.  Will it work on the other platforms?  Probably, but I haven't tested it on any but Desktop, so that is why I'm suggesting you do the same.  Just copy and paste this code over the main.qml and it should run.


import QtQuick 1.0

Rectangle {
    width: 400
    height: 400

    Rectangle {
        id: applyButton

        width: 100
        height: 30
        border.color: "#4f78a2"
        border.width: 2
        radius: 5
        smooth: true
        anchors.centerIn: parent
        color: "#BFEFFF"
        opacity: 1.0

        Text {
            id:textItem
            anchors.centerIn: parent
            font.pointSize: 12
            font.family: "Helvetica"
            color: "#337777"
            styleColor: "#ffffff"
            style: Text.Raised

            text: "Apply"
        }

        PropertyAnimation {
            id: changeToColor1;
            target: applyButton;
            properties: "color";
            to: "#ffff00";
            duration: 1000
        }

        PropertyAnimation {
            id: changeToColor2;
            target: applyButton;
            properties: "color";
            to: "#BFEFFF";
            duration: 1000
        }

        NumberAnimation {
            id: toFullOpacity
            target: applyButton
            properties: "opacity"
            to: 1
            duration: 250
            exclude: border
        }

        SequentialAnimation {
            id: sequentialOpacity
            running: false

            NumberAnimation {
                id: animateOpacity
                target: applyButton
                properties: "opacity"
                from: .2
                to: 1
                duration: 700
                easing {type: Easing.InOutQuad; }
                exclude: border
            }
            NumberAnimation {
                id: animateOpacity2
                target: applyButton
                properties: "opacity"
                to: .2
                from: 1
                duration: 700
                easing {type: Easing.InOutQuad;}
                exclude: border
            }
            loops: Animation.Infinite
        }

        MouseArea {
            id: applyButtonMA
            anchors.fill: parent
            //hoverEnabled: true
            onClicked: {
                if (sequentialOpacity.running == true)
                {
                    sequentialOpacity.stop()
                    toFullOpacity.start()
                    changeToColor2.start()
                }
                else
                {
                    changeToColor1.start()
                    sequentialOpacity.start()
                }
            }
        }
    }
}

                                         



When you click the button the first time, it will turn to yellow and start to pulse ( the opacity will cycle from 1.0 to 0.1 and back again over and over ).

When you click it again, it will return to it's initial state as a light blue button.  

I really love how you just put an id on an item and then you can refer to it later by that id.  Like:
   sequentialOpacity.stop()

It's quick object notation.  Since sequentialOpacity (my name) is an instance of SequentialAnimation I can use dot notation to access any of SequentialAnimation's functions.

QML is not exactly the "plain english" language that it appears to be.  Even the syntax can get a bit wonky at times and leave me scratching my head as to WHY is this element in this syntax, while all the rest are written a different way.  For example, take this bit of code from above:


            NumberAnimation {
                id: animateOpacity2
                target: applyButton
                properties: "opacity"
                to: .2
                from: 1
                duration: 700
                easing {type: Easing.InOutQuad;}
                exclude: border
            }
Apparently "easing" is an object? All the other properties use the colon notation, but then easing pops in using the syntax of an entire object. It could have been written like this:

 
            NumberAnimation {
                id: animateOpacity2
                target: applyButton
                properties: "opacity"
                to: .2
                from: 1
                duration: 700
                easing {
                   type: Easing.InOutQuad;
                }
                exclude: border
            }
Thinking of easing as a property had me coding with the wrong syntax for a while, and the error messages are not always specific enough to lead to proper correction. Eventually I ran into just one example on the inter-webs with the proper syntax and I fixed it, but it took some digging and sleuthing, and this sort of thing is a serious waste of valuable time.

"exclude: border" does not work either, by the way. I have no idea why. And QtCreator rejected entirely "exclude: border.color". Gave up on that one.

 Anyway, play with this and see if it helps you understand QML a little better. Let me know if you have any suggestions or questions. I've been working with QML for a couple of months now, and I've learned how to do a few things. If you are learning this powerful language ( and possibly Qt alongside of it as well ) then you have probably found that documentation of some of the simplest things is hard to find. I'm one who believes that documentation needs to include comprehensive examples, definitions and references to relative terms if it dares call itself documentation. As "extensive" as the Qt and QML documentation is, it lacks terribly in explanations, clarifications of concepts, and easy to read specific examples. IF you already know what you are doing, then it is an adequate reference, but even then I often run into dead ends.

Here are some more of my thoughts on that whole situation...

Thanks for reading.

 CHEERS! ultramanjones

2012-08-09

Qt Open Source Platform sold/moved to Digia

As per this article at PCMag.com, Nokia has just sold Qt to Digia.

I consider this to be great news.  I was a bit worried that Qt might die or flounder along with Nokia, considering that Nokia has completely lost their minds.  Perhaps more accurately, they have been taken over by a questionable leader, to say the least.  I'll not get into the politics.

I'm hopeful that this will lead to a quick release of Qt 5.0, a full realization of QML tools and standards, and full support for Android (and possibly MeeGo, that would be dreamy!).

So glad to hear that the core team will be kept together.

Great news!

I LIKE it!

2012-08-03

Operator Malfunction

When I was a kid, my bro and I used to always get on my Dad's Commodore 64 and try to program ( or just play games ).  I remember that sometimes we would run out of the "office" and get Dad, who was most likely watching TV or reading in the living room, and we'd say things like, "Dad!  We can't get this stupid thing to work, it keeps hanging up and just not working!", or some similar desperate, oblivious plea.

He would "hrrrumph" as he got up from the floor and start following us back to the computer, whereupon I would hear him say, "Ah... it's probably just operator malfunction."

The first couple times I didn't ask what he meant, because I liked to think that I was smart and I would just figure it out when he showed us what was wrong anyway.

Then one time he said the phrase again, and I realized that I had no idea what he was talking about so I said, "What do you mean by 'operator malfunction'?  What's the operator?"

My brain rapidly shuffled through images of circuit boards, transistors and all manner of mysterious electrical components trying to figure it out.

He poked me in the forehead, holding his finger there, then pushing away as he said,"YOU operate the computer, right?" I watched him slowly smile as he watched the me grasp the concept and then he laughed that belly chuckle, "heh ha!", as I scowled and twisted my face at the idea that it could possibly be my fault.

"Ahhh...", I said, reluctantly, but smiling as we sat down to figure out the problem.

Sometimes, after that,  he would hold his finger up in the air like Einstein and proclaim, "Operator Malfunction!"

To this day, I find that the vast majority of my computing problems are due to "operator malfunction".

Miss you Dad.

2012-07-13

QTreeView in QtQuick/QML Implementation

Okay, so in my last post I posted a duplicate of my question over on the Qt Dev Forums.  Thankfully someone answered quickly and I was able to implement a solution.  Mind you, it still has all sorts of kinks and functions that need to be fixed or realized, but it's a start.  Considering how much time I spent trying to get this to work, I figured that this is one of those things that I really want to share with the community, so before I delve in deep, I thought I'd stop for a second and post the code to my test application.

All this app does is show a QTreeView using QML.  Essentially, it is a boiled down plugin for QML.  The QTreeView class is derived from QWidget.  The QDeclarativeView where my QML "lives" only accepts elements that are derived from QGraphicsObject.  To solve this problem I have wrapped the QTreeView in a QGraphicsProxyWidget.

It sounds complicated, but it really isn't.  Without ever having seen it done however, it was quite difficult to discover,  especially for the nooborn like me.  Answers are much simpler to find once you know what questions to ask.  IMHO it is important to always remember this fact lest we start to labor under the misconception that we are actually intelligent beings or that we ourselves are awesome because we know so muich.  What follows are the terrible diseases that go by many names including "noobphobia", "lorditoverallsia", "assholiosis", and "I-have-forgotten-plain-english-but-I-think-that-using-technical-terms-makes-me-look-smart-so-no-one-knows-what-I-am-saying-blindness".  Just take a look around the forums and through the comments all over the web and you will see that these diseases are spreading like that virus that causes people to turn into flesh eating zombies in the movies.  I think I'd prefer the zombies....

Anyway, here is the code.  Enjoy.  If you have any questions, I'll try to answer, but I'm a noob too, so no promises peeps!

I am using Qt Creator 5.0 Based on Qt 4.8.1 (64 bit) according to Help/About Qt Creator...


This quick test app was created by going to File/New File or Project.../Applications/Qt Quick Application (Built-in Elements). Named the project QTreeTest.  I chose only "Desktop" as my target.


The files I am going to share are:

QTreeTest.pro
testtron.h
treeview.h
testtron.cpp
main.cpp
main.qml
TreeView.qml

I tried to post the code directly to Blogger and it got all wonky of course, so here is a link to a Google Docs folder instead.  Enjoy!

LINK TO ALL THE FILES


NOTE: In order to assign the "treeView" a "hide" state I had to nest it within another rectangle and assign the hide state to the id of that rectangle. The TreeView will reject direct state assignments.
I sure hope this helps somebody. I'm going to come back and clean this up a bit on Monday. Right now, it is almost 6:00 PM and it is FRIDAY! Woo hoo! I am outta here! Cheers!

2012-07-12

QTreeView in QML question (posted to Qt Developer Network too)

UPDATE:  See my later post here for the answer(s) to this question.  Or at least a start.

Hello everybody.  Help!  I'm trying to incorporate a Model/View into an application using QTreeView, QFileSystemModel and qmlRegisterType to create the QTreeView plugin.

If my main.qml looks like this:

import QtQuick 1.1
import TreeView_Plugin 1.0

    TreeView {
        id: myTreeView
        allColumnsShowFocus: true

    }

I get a QTreeView displayed looking like this:



However, when my main.qml looks like this:

import QtQuick 1.1
import TreeView_Plugin 1.0

Rectangle {
    id:myRect
    width: 400
    height: 400

    TreeView {
        id: myTreeView
        allColumnsShowFocus: true
    }
}

All I get is this...


I am not able to insert the "TreeView" into the rest of my QML and I can't figure out why.
If I try to add a property change to x, y, width or height, for example:

    TreeView {
        id: myTreeView
        x: 15
        y: 15
        allColumnsShowFocus: true
    }


I get error:  Invalid property assignment: "x" is a read-only property

Of course I will post plenty more code if someone thinks they might be able to help.

The application already uses a QDeclarativeView with an OpenGL backend like so:

QGLWidget *glWidget = new QGLWidget(this); 
setViewport(glWidget); 
 setViewportUpdateMode(QGraphicsView::FullViewportUpdate);


There is of course a bit more code involving setting the FileSystemModel, etc, but I don't believe it is relevant.  I am really quite baffled here.  Obviously, I need the QTreeView to show within the rest of my QML or there really is no point.

If anyone could point me to a way to do this, I would very much appreciate it.  I'm pretty new to Qt and I readily admit that I sometimes have no idea what is going on "under the hood", especially when it comes to the whole MOC file paradigm.

Whatever way I can get this done is fine with me.  I really thought the plugin (qmlRegisterType) method was the way to go, because I'm using it to create an OpenGL window for animations in a separate part of the app, but, as you can see, it ain't working.

Thanks for your help!
------------------------------------
UPDATE  2012-07-13:
I received an answer in the Qt Dev Forums.  Here's a link.
This looks promising, because I was already thinking I would probably have to wrap the class/object in another object in order to get QDeclarativeView to accept it.

What I did not see until after I posted this yesterday, is that QtCreator is producing a warning when I run the first example above (the one WITH the QTreeView displayed).  I don't have it in front of me but it was something along the lines of QDeclarativeView only supports objects derived from QGraphicsObject.  QTreeWidget is NOT a QGraphicsObject, it is derived from QWidget.

I'll let you know what I get working.

I know it's a bit odd posting a question like this, but now you can see the sort of process I go through on a daily basis in the world of programming.  The eternally nooborn, learning never ends.  (did I just coin a word?)

2012-05-29

QtCreator error: No GL capable X visuals available Fedora 16 Linux


So you are trying to run the example applications in Qt Creator to see if you have installed correctly and you get:

No GL capable X visuals available.

Well, if you are running Fedora 16 with an nVidia graphics card then this link might just help you fix that problem.  The methods described here have only been tested on a Fedora 16 system running Qt Creator 2.5 installed on Qt SDK 1.2.1 and with an nVidia GeForce GT 240 graphics card.  So try at your own risk, because changing your graphics drivers obviously could cause major problems (i.e. you won't be able to see anything!!)

http://www.if-not-true-then-false.com/2011/fedora-16-nvidia-drivers-install-guide-disable-nouveau-driver/

Many thanks to if-not-true-then-false!

Uh oh!  So you did that and it STILL gives you the error.  Well then try this guy's advice.  It worked for me.

http://www.opengl.org/discussion_boards/showthread.php/176711-QGLWidget-under-new-OS-configuration-throws-error

Just look on the left panel of Qt Creator.  Just below the "Debug" bug icon, there is a sideways folder thing called Projects.  Click on it.  At the top you will see a funny looking widget that looks like this:


Make sure you have "Run" clicked.  (I know, right?  Why do they make it like solving some kind of hieroglyphic puzzle in an Indiana Jones movie?  I mean who is looking for a thing that looks like that for switching pages?)  Anyway...

After you make sure you are looking at the Run Settings page.  Scan down and find "Run Environment".  Look over to the right and click on "Details", if it isn't open already, and then scan the list until you find:
LD_LIBRARY_PATH
Click on it and then click on the "Unset" button on the right.

That should do it.  Now go back to the "Welcome" screen of Qt Creator 2.5 and select "Examples" and run one of them.  Works for me.

No warranties or promises here.  Good luck.

Cheers!

UPDATE:  While this did work for the 2dpainting example, I ran into a new problem.  When I tried to open an existing project (of mine) and run it.  I actually copied this project over from another work station.  I copied the entire project folder and placed it in my working directory.

The first problem was that I got this error:
Failed to start program. Path or permissions wrong?

I fixed this by selecting Build>Rebuild project...
Now it tried to run, but then it went back to the error:
QGLTempContext: No GL capable X visuals available.

So I picked up my computer and threw it out the window and...  No wait that was just a daydream.
I went BACK into the Projects>Run Settings (as described above) and found that the LD_LIBRARY_PATH was set again.  I unset it and now it works.  My project was "Set as Active Project" when I did this.  To set any project as "active" just right click on it and click the first selection.  Does this mean that I will have to do this for every project?  Not sure yet.  We shall see......

Install QtCreator 2.5 Linux Fedora from the binary (.bin) download

What I am describing here is kind of noob stuff, but then that's what I do :  kick ass for the noobs every day.

You will need to have already installed the Software Development Kit before you do this.  Currently, on May 29, 2012, the latest version of the Qt SDK is 1.2.1.  You can get the installer here.  For my installation I used the Linux 64 bit Offline Installer.  This will also install QtCreator 2.3.1 as part of the whole package.  Now, since they haven't (yet) released an SDK that includes QtCreator 2.5, you can just grab the binary here and install it yourself.

Download it, it should be about 98mb so it will depend on your connection speed how long it takes.
Open the folder where you downloaded it.
Right click on it.  It should look like this:  qt-creator-linux-x86_64-opensource-2.5.0.bin
Select properties.
Select the permissions tab.
Check the box for "Allow executing file as program."

Now I would just say, "Now double-click on it", but that didn't work for me.  It gave me some error:

Could not display "/home/ultrajones/Downloads/q...x-x86_64-opensource-2.5.0.bin"

The file is of an unknown type

No it isn't.
So open a terminal and CD to the directory where you downloaded it.  Most likely this is the Downloads folder in your Home directory.  When you open a terminal you will already be in the Home directory, so just type:

cd Downloads

And you will be there.
Type:

ls

You will see a list of all the files and folders in that directory.
Somewhere on the list you should see:

qt-creator-linux-x86_64-opensource-2.5.0.bin

Here's a nice trick.  Now type:

./qt-

and hit the tab key.  The terminal should fill out the rest of the name for you, since it is the only thing in the folder with a name starting with "qt-".  Oooh magic.  By the way, the dot ( . ) stands for current directory and the slash ( / ) just tells the terminal to execute the following file.  Now just hit enter and the installer should fire up.  

If it didn't, don't blame me.  I do this for free!  

Cheers!

2012-05-27

YouTube is blue!

All my other visual media are fine, but YouTube is blue!

Or I should say, it WAS blue.  I figured out how to fix it.  At least temporarily.  Thanks to this link:


Another thumbs down for Flash.

2012-05-26

Create a file listing all files in directory Linux

This is really simple stuff, but, since I never had a formal Linux class, I never knew!

To create a .txt file listing all the files in a directory simply enter:

ls > anyfilenameyouwant.txt

I wanted to create a text file that listed all of the MP3's in my Home/Music directory.  Good thing I was using Linux, because this incredibly simple task is impossible without installing software in Windows.  It is really quite powerful for getting things done!

All I had to do was.  Open a terminal.  CD to the Music directory and enter:

ls *.mp3 > mp3list.txt

mp3list.txt is just a name I made up on the spot.  The file did not yet exist, but it does now!

Another neat little trick I learned is to create an alphabetized version of a file.  This should only be done with simple files like .txt or .dat.  You see I had been compiling a list of songs that I wanted to add to a compilation I am going to burn for someone, and they were not in any sort of order.  I wanted the list to be alphabetical for readability purposes.

cat my_mix.txt |sort -d my_mix_AZ.txt

That's it!  It creates the my_mix_AZ.txt file on the fly.  Just be very careful with this.  If you designate the second file the same as the first it will erase everything.  I found out the hard way.  Luckily I had another copy laying around in my messy folders.

Now I can take the two files and diff them using Meld, or just eyeball them side by side to find differences so much easier now that I have alphabetical versions.

2012-05-21

Fedora 16 Enable Keeping Files and Folders on Desktop

So you installed Fedora 16 (with Gnome 3) and now you are all like "Yo?  Why can't I put folders and files on my desktop?  What is a desktop FOR if I can't put stuff on it!?!!"  Actually that was ME.

So just open a terminal and enter this:

sudo yum install gnome-tweak-tool

Then type this:

gnome-tweak-tool

There you go.  Try the options and your desktop will be useful again.  ALSO, if you have installed Fedora 16 on a laptop you can change the laptop lid close actions options, like whether it goes to sleep or just turns off or does nothing (which is nice if you are hooking it up to a monitor and using it as a workstation.)

Cheers!


2012-05-14

Flash plugin not showing up in Chrome Fedora Linux

I worded that title to try and make it easy to find this post.  This is the second time I had to deal with this and so I thought I'd better record a post, since I couldn't remember how I did it the first time, it had been so long.

I remember now!

Problem:  If you go to a site that uses Flash, like Pandora, you get a message telling you to install the latest version of Flash plugin.  Flash plugin is nowhere, even after installing through YUM or apt (ubuntu software center).

Google, meanwhile, will tell you that Flash is already installed in Chrome, because the latest versions, for a few years now, are bundled with Flash.  But it sure isn't working.  So what gives?

Even when you type "about:plugins" in the address bar in Chrome there is absolutely no listing for Flash.  It SHOULD say Shockwave Flash, but it just isn't there.  Manually installing it and all of the other advice you find on most forums will be completely useless.

Never fear - THIS site has the solution.  In a nutshell, you will need to install the latest Flash in Firefox, before it will start working in Chrome.  Messed up huh?  There are also some other command line things they give you over there and I just did them all just to make sure, but I think some are unnecessary once you get the Firefox plugin installed.

How my hours of Googling did not lead me straight to this Fedora Project page, I have no idea.

Enjoy.

2012-05-11

Good QML QtQuick C++ Tutorial (finally)

I searched long and hard for something like this, so I thought I'd pass it along to those who are Googling for the same thing.  There are tons of tutorials and samples and examples out there that use the Qt API with C++, but I found it quite difficult to find any complete and comprehensive tutorials and/or code that includes the method that integrates QML as the User Interface and C++ for the application logic.  Here's what I was looking for:

http://kgronholm.blogspot.com/2010/10/qt-quick-game-programming.html

or here

http://quitcoding.com/?page=work#qtquick

Thanks to Kaitsu and QUIt Coding for the good work and generosity.

Some notes on installation:

I had to install mesa-libGLU-devel in my Fedora 16 system in order to get the game to run.

I had another problem getting the game to run.  Although the project would build, when I tried to run it I would get an error saying "No such file or directory" referring to the "content" folder where all of the QML is kept.  The build was not copying this folder into the shadow build copy that it was then attempting to run from.

So I sent an email to QUItcoding.com.  Kaitsu answered me back very quickly and let me know that I only needed to disable "shadow build" under the build settings in the "projects" view ( found on the left side of QtCreator).  That fixed the issue immediately.

I should also mention that I replaced the line:
import Qt 4.7

at the top of all the .qml files with:
import QtQuick 1.0

I don't think this really mattered since the newer versions retain previous version functionality, but I thought I'd mention it anyway.



2012-03-30

Add existing project to SVN repository with Subclipse

First of all setup an SVN repository.  I'm no expert on this.  I can tell you that if you set up a free one with Codesion, that you will be stepped through the process immediately after you sign up.  I do recall that their setup wizard directed me to the Linux command line a lot;  it didn't seem Windows friendly (fine with me).

You will also need to install Subclipse in Eclipse.  Tigris.org releases it and they have this page with a list of releases and the appropriate url's.  Please read that page carefully, because it is important that you install the right version for your installation.  (In Eclipse everything depends on other things, that's why they call them dependencies...)  Basically, Subclipse installs on top of Subversion, so you might want to read up on this stuff before you break Eclipse.  This is a huge point, because Eclipse breaks very easily;  once you add something to Eclipse it seems near impossible to remove it.  It will SAY it's removed, but elements of it will show up and haunt you like those evil little pac-man ghosts.  So, especially for beginners, I recommend that you do NOT monkey around with your Eclipse installation.  For instance, don't just install plugins to try them out, thinking that you will be able to cleanly remove them.  Nope, they will not remove cleanly.  You will end up having to completely track down every piece of Eclipse and all of its plugins, and associated folders, and references in the .bashrc folder, kill them, chop off their heads, steak them and set them on fire.  Then kill Eclipse (steak it and set it on fire).  And then re-install from scratch and re-install everything you want.  And that still might not work.  Cockroaches kill easier.  So be careful.

Alright then... back to the topic at hand.

Once you've discovered which release of Subclipse you need to install, and have all the dependencies lined up, go to "Help/Install New Software" in Eclipse.

Click the "Add" button on the upper right.  Name it whatever makes sense to you:  "Subclipse 1.6" might be good.  Enter the url in the bottom field.

Now you should be able to select that url listing in the "Work with:" field at the top of the "Available Software" screen.  Click the drop down menu and select it. You may need to wait a minute while Eclipse updates itself.

Then find "Subclipse" and check the box next to it. (This will check all of the boxes under this heading, which is a good idea, because it includes some dependencies like the JavaHL Native Library Adapter, which is required.)  Eclipse will do it's thing, and, if all goes well, you now have Subclipse installed.

Create a project in Eclipse, the usual way.

Right click on the project in Eclipse.  Mouse almost all the way down and select "Team/Share Project..."  Step through the dialog boxes that pop up, entering all the appropriate information.  (You will need your repository information during this process).  It goes like this:

"Team/Share Project..."
select "SVN"
select "Use existing repository location"
select "Use project name as folder name" (you don't HAVE to)
enter the URL into the "URL:" field
(for example: "https://mycompany.svn.cvsdude/project/helloworld"  helloworld being the name of the project we are adding to the SVN repo)
click Finish
You'll get a drop down screen on top of Eclipse talking about the Synchronize view.  I recommend checking the "Remember my decision" box and then clicking "Yes", because we need to go over there and finish the process, before we forget (SVN might bite you if you don't!).

Now you will see the "Synchronize" panel on the left side of Eclipse.  On the upper left of the panel is a little button showing a tiny picture of a 2 ended arrow pointing from a window to a yellow cylinder and back again.  Hover over it.  A tooltip will pop up saying "Synchronize SVN"  It may even actually have in parentheses the name of the project that we just added to the repository.  Right now, the project is added, but the Subclipse plugin and the SVN server are not synchronized.
Click that button.
A busy little dialog will pop up and fill a loading bar.
Finally, hover over a little button on the upper right of the panel.  It is the "Commit All Outgoing Changes... " button.  Click it!
A dialog box appears.  Enter a comment in here.  Try and make it descriptive, because you may want to search for it at a later date and "Commit of Glory" probably won't ring a bell in the future.  For this instance, "First Commit" will suffice.
That should do it.
You'll see the SVN "Checking in" box loading up.  Afterwards, the Synchronize panel will say something like "No changes in 'SVN (/Helloworld)'."

I took some screenies, I'll get them attached later.

2012-03-23

Joomla - create a profile plugin with custom fields

This plugin is based on the code found here:
http://docs.joomla.org/Creating_a_profile_plugin


Like I mentioned in an earlier post, where I showed how to add custom fields to the profile plugin that is already included with Joomla, the joomla example is very useful, but doesn't really get into adding new fields.  What I recommend is comparing that code with my code to see what I changed.  Also you can refer to my old post for some guidance.  I would use a diff tool like Meld.  To install in Fedora 16 just type:


yum install meld
in a command line terminal.


These files need to be created inside of your Joomla 2.5.4 installation.  The paths given are relative to the root of the installation.  These will not be overwritten during updates, because these names and paths do not exist in the original, but I do keep some backups, just in case.


The below 5 files comprise the entire plugin. First, create them all in their appropriate places on the server. (Just click the links below to download the files).


Then just go to the Extension Manager: Discover tab in the Joomla Administrator panel in the back end and click the blue "Discover" button on the upper right.  If you've done everything right, Joomla should see it listed as "Profile 7".  Check the box next to it and then click the yellow "Install" button on the upper right.  It should be ready to go.  You now should be able to find it in Joomla, Plug-in Manager: Plug-ins, and enable it.  Be sure and disable any other profile plugins you may have running, including the stock Joomla Profile plugin, or there could be conflicts OR they will both be displayed on your register and profile edit pages!

/administrator/language/en-GB/en-GB.plg_user_profile7.ini
/administrator/language/en-GB/en-GB.plg_user_profile7.sys.ini

(I want to point out that I originally posted the wrong path for the last file above as:
 /plugins/user/profile/profiles/profile.xml
I was missing a "7" there.  Thanks to Patrick for pointing that out, and sorry for any trouble this may have caused to anyone who was trying this.)

Please note, that the last file listed above is "profile.xml", not profile7 like the others.  This is VERY important.  Be careful!  These locations are in the Joomla installation.  Create them all with gedit or your text editor of choice (or just download them, now that I've posted links) and place them in their places on your server using an FTP client (or however you can get them there).  I use FileZilla.  (Sorry, but I don't have time to give a tut on using FTP or any other method of writing files to your server, maybe some other time.)

Here are the files.  I tried to highlight in blue the differences between my plugin and the standard plugin, I may have missed highlighting a "7" on a "Profile 7" here or there - they are peppered throughout all 5 files and finding and creating these inside the original code was the biggest challenge of the entire project.  (You see I couldn't just leave it with the name "profile" because then it would be overwritten every time you update, just like the standard plugin.) I will post both the content and links for download:
( NOTE:  I would LOVE to have these files posted in a prettier format.  If you happen to know a way to post frames inside of blogger or know anything that would make these look better, please let me know!)

en-GB.plg_user_profile7.ini (click for download)
-------------------------------------------------------------------------------------------------------------------

; Joomla! Project
; Copyright (C) 2005 - 2012 Open Source Matters. All rights reserved.
; License http://www.gnu.org/licenses/gpl-2.0.html GNU/GPL, see LICENSE.php
; Note : All ini files need to be saved as UTF-8

PLG_USER_PROFILE7_XML_DESCRIPTION="User Profile 7 Plug-in"
PLG_USER_PROFILE7="User - Profile 7"
PLG_USER_PROFILE7_SLIDER_LABEL="User Profile 7"
PLG_USER_PROFILE7_FIELD_ABOUT_ME_DESC="Choose an option for the field About Me."
PLG_USER_PROFILE7_FIELD_ABOUT_ME_LABEL="About Me:"
PLG_USER_PROFILE7_FIELD_ADDRESS1_DESC="Choose an option for the field Address1"
PLG_USER_PROFILE7_FIELD_ADDRESS1_LABEL="Address 1:"
PLG_USER_PROFILE7_FIELD_ADDRESS2_DESC="Choose an option for the field Address2"
PLG_USER_PROFILE7_FIELD_ADDRESS2_LABEL="Address 2:"
PLG_USER_PROFILE7_FIELD_CITY_DESC="Choose an option for the field City"
PLG_USER_PROFILE7_FIELD_CITY_LABEL="City:"
PLG_USER_PROFILE7_FIELD_COUNTRY_DESC="Choose an option for the field Country"
PLG_USER_PROFILE7_FIELD_COUNTRY_LABEL="Country:"
PLG_USER_PROFILE7_FIELD_COUNTRY_MESSAGE="Country Required"
PLG_USER_PROFILE7_FIELD_DOB_DESC="Choose an option for the field Date of Birth"
PLG_USER_PROFILE7_FIELD_DOB_LABEL="Date of Birth:"
PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_DESC="Choose an option for the field Favourite Book"
PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_LABEL="Favourite Book:"
PLG_USER_PROFILE7_FIELD_NAME_PROFILE_REQUIRE_USER="User profile fields for Profile 7 edit form"
PLG_USER_PROFILE7_FIELD_NAME_REGISTER_REQUIRE_USER="User profile fields for registration and administrator user Profile 7 forms"
PLG_USER_PROFILE7_FIELD_PHONE_DESC="Choose an option for the field Phone"
PLG_USER_PROFILE7_FIELD_PHONE_LABEL="Phone:"
PLG_USER_PROFILE7_FIELD_POSTAL_CODE_DESC="Choose an option for the field Postal Code"
PLG_USER_PROFILE7_FIELD_POSTAL_CODE_LABEL="Postal / ZIP Code:"
PLG_USER_PROFILE7_FIELD_POSTAL_CODE_MESSAGE="Postal Code Required"
PLG_USER_PROFILE7_FIELD_REGION_DESC="Choose an option for the field Region"
PLG_USER_PROFILE7_FIELD_REGION_LABEL="Region:"
PLG_USER_PROFILE7_FIELD_TOS_DESC="Agree to terms of service"
PLG_USER_PROFILE7_FIELD_TOS_LABEL="Terms of Service"
PLG_USER_PROFILE7_FIELD_WEB_SITE_DESC="Choose an option for the field Web Site"
PLG_USER_PROFILE7_FIELD_WEB_SITE_LABEL="Web site:"
PLG_USER_PROFILE7_OPTION_AGREE="Agree"
PLG_USER_PROFILE7_OPTION_YES="YES"
PLG_USER_PROFILE7_FIELD_SUBSCRIBE_DESC="Subscribe to get emails about updates"
PLG_USER_PROFILE7_FIELD_SUBSCRIBE_LABEL="Receive Update Emails"
-------------------------------------------------------------------------------------------------------------

-------------------------------------------------------------------------------------------------------------
; Joomla! Project
; Copyright (C) 2005 - 2012 Open Source Matters. All rights reserved.
; License http://www.gnu.org/licenses/gpl-2.0.html GNU/GPL, see LICENSE.php
; Note : All ini files need to be saved as UTF-8

PLG_USER_PROFILE7="User - Profile 7"
PLG_USER_PROFILE7_XML_DESCRIPTION="User Profile 7 Plug-in"
-------------------------------------------------------------------------------------------------------------

-------------------------------------------------------------------------------------------------------------

/**
 * @copyright Copyright (C) 2005 - 2012 Open Source Matters, Inc. All rights reserved.
 * @license GNU General Public License version 2 or later; see LICENSE.txt
 */

defined('JPATH_BASE') or die;

jimport('joomla.utilities.date');

jimport('joomla.user.helper');


jimport('joomla.user.user');


jimport('joomla.utilities.arrayhelper');


/**
 * An example custom profile plugin.
 *
 * @package Joomla.Plugin
 * @subpackage User.profile
 * @version 1.6
 */
class plgUserProfile7 extends JPlugin
{
/**
* Constructor
*
* @access      protected
* @param       object  $subject The object to observe
* @param       array   $config  An array that holds the plugin configuration
* @since       1.5
*/
public function __construct(& $subject, $config)
{
parent::__construct($subject, $config);
$this->loadLanguage();
}

/**
* @param string $context The context for the data
* @param int $data The user id
* @param object
*
* @return boolean
* @since 1.6
*/
function onContentPrepareData($context, $data)
{
// Check we are manipulating a valid form.
if (!in_array($context, array('com_users.profile', 'com_users.user', 'com_users.registration', 'com_admin.profile'))) {
return true;
}

if (is_object($data))
{
$userId = isset($data->id) ? $data->id : 0;

if (!isset($data->profile) and $userId > 0) {

// Load the profile data from the database.
$db = JFactory::getDbo();
$db->setQuery(
'SELECT profile_key, profile_value FROM #__user_profiles' .
' WHERE user_id = '.(int) $userId." AND profile_key LIKE 'profile7.%'" .
' ORDER BY ordering'
);
$results = $db->loadRowList();

// Check for a database error.
if ($db->getErrorNum())
{
$this->_subject->setError($db->getErrorMsg());
return false;
}

// Merge the profile data.
$data->profile7 = array();

foreach ($results as $v)
{
$k = str_replace('profile7.', '', $v[0]);
$data->profile7[$k] = json_decode($v[1], true);
if ($data->profile7[$k] === null)
{
$data->profile7[$k] = $v[1];
}
}
}

if (!JHtml::isRegistered('users.url')) {
JHtml::register('users.url', array(__CLASS__, 'url'));
}
if (!JHtml::isRegistered('users.calendar')) {
JHtml::register('users.calendar', array(__CLASS__, 'calendar'));
}
if (!JHtml::isRegistered('users.tos')) {
JHtml::register('users.tos', array(__CLASS__, 'tos'));
}
if (!JHtml::isRegistered('users.subscribe')) {
JHtml::register('users.subscribe', array(__CLASS__, 'subscribe'));
}
}

return true;
}

public static function url($value) { if (empty($value)) { return JHtml::_('users.value', $value); } else { $value = htmlspecialchars($value); if(substr ($value, 0, 4) == "http") { return '<a href="'.$value.'">'.$value.'</a>'; } else { return '<a href="http://'.$value.'">'.$value.'</a>'; } } }

public static function calendar($value)
{
if (empty($value)) {
return JHtml::_('users.value', $value);
} else {
return JHtml::_('date', $value, null, null);
}
}

public static function tos($value)
{
if ($value) {
return JText::_('JYES');
}
else {
return JText::_('JNO');
}
}

public static function subscribe($value)
{
if ($value) {
return JText::_('JYES');
}
else {
return JText::_('JNO');
}
}

/**
* @param JForm $form The form to be altered.
* @param array $data The associated data for the form.
*
* @return boolean
* @since 1.6
*/
function onContentPrepareForm($form, $data)
{

if (!($form instanceof JForm))
{
$this->_subject->setError('JERROR_NOT_A_FORM');
return false;
}

// Check we are manipulating a valid form.
$name = $form->getName();
if (!in_array($name, array('com_admin.profile', 'com_users.user', 'com_users.profile', 'com_users.registration'))) {
return true;
}

// Add the registration fields to the form.
JForm::addFormPath(dirname(__FILE__).'/profiles');
$form->loadFile('profile', false);

$fields = array(
'address1',
'address2',
'city',
'region',
'country',
'postal_code',
'phone',
'website',
'favoritebook',
'aboutme',
'tos',
'dob',
'subscribe',
);

foreach ($fields as $field) {
// Case using the users manager in admin
if ($name == 'com_users.user') {
// Remove the field if it is disabled in registration and profile
if ($this->params->get('register-require_' . $field, 1) == 0 &&
$this->params->get('profile-require_' . $field, 1) == 0) {
$form->removeField($field, 'profile7');
}
}
// Case registration
elseif ($name == 'com_users.registration') {
// Toggle whether the field is required.
if ($this->params->get('register-require_' . $field, 1) > 0) {
$form->setFieldAttribute($field, 'required', ($this->params->get('register-require_' . $field) == 2) ? 'required' : '', 'profile7');
}
else {
$form->removeField($field, 'profile7');
}
}
// Case profile in site or admin
elseif ($name == 'com_users.profile' || $name == 'com_admin.profile') {
// Toggle whether the field is required.
if ($this->params->get('profile-require_' . $field, 1) > 0) {
$form->setFieldAttribute($field, 'required', ($this->params->get('profile-require_' . $field) == 2) ? 'required' : '', 'profile7');
}
else {
$form->removeField($field, 'profile7');
}
}
}

return true;
}

function onUserAfterSave($data, $isNew, $result, $error)
{
$userId = JArrayHelper::getValue($data, 'id', 0, 'int');
//
//BEGIN CUSTOM CODE
//
//put this inside the onUserAfterSave function in profile7.php
// This code will check if the user clicked the radio button for email
// updates by checking the 'subscribe' boolean in the data
// then assign the user to that group (group 9) if true
$groupID = 9; //9 is the value for the subscriber group in the ACL
//DEBUG code that forces if statement to come up true:
//$subscribeFlag = 1;
if ($userId && (isset($data['profile7']['subscribe'])))
{
$subscribeFlag = ($data['profile7']['subscribe']);
if (!($subscribeFlag == 0)) 
{
try
{
JUserHelper::addUserToGroup($userId, $groupID);
}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}
else
{
try
{
JUserHelper::removeUserFromGroup($userId, $groupID);
}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}
}
//END CUSTOM CODE
//
if ($userId && $result && isset($data['profile7']) && (count($data['profile7'])))
{
try
{
//Sanitize the date
if (!empty($data['profile7']['dob'])) {
$date = new JDate($data['profile7']['dob']);
$data['profile7']['dob'] = $date->format('Y-m-d');
}

$db = JFactory::getDbo();
$db->setQuery(
'DELETE FROM #__user_profiles WHERE user_id = '.$userId .
" AND profile_key LIKE 'profile7.%'"
);

if (!$db->query()) {
throw new Exception($db->getErrorMsg());
}

$tuples = array();
$order = 1;

foreach ($data['profile7'] as $k => $v)
{
$tuples[] = '('.$userId.', '.$db->quote('profile7.'.$k).', '.$db->quote(json_encode($v)).', '.$order++.')';
}

$db->setQuery('INSERT INTO #__user_profiles VALUES '.implode(', ', $tuples));

if (!$db->query()) {
throw new Exception($db->getErrorMsg());
}

}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}

return true;
}

/**
* Remove all user profile information for the given user ID
*
* Method is called after user data is deleted from the database
*
* @param array $user Holds the user data
* @param boolean $success True if user was succesfully stored in the database
* @param string $msg Message
*/
function onUserAfterDelete($user, $success, $msg)
{
if (!$success) {
return false;
}

$userId = JArrayHelper::getValue($user, 'id', 0, 'int');

if ($userId)
{
try
{
$db = JFactory::getDbo();
$db->setQuery(
'DELETE FROM #__user_profiles WHERE user_id = '.$userId .
" AND profile_key LIKE 'profile.%'"
);

if (!$db->query()) {
throw new Exception($db->getErrorMsg());
}
}
catch (JException $e)
{
$this->_subject->setError($e->getMessage());
return false;
}
}

return true;
}
}
----------------------------------------------------------------------------------------------------------------

----------------------------------------------------------------------------------------------------------------
<?xml version="1.0" encoding="utf-8"?>
<extension version="2.5" type="plugin" group="user">
<name>plg_user_profile7</name>
<author>Joomla! Project</author>
<creationDate>January 2008</creationDate>
<copyright>(C) 2005 - 2012 Open Source Matters. All rights reserved.</copyright>
<license>GNU General Public License version 2 or later; see LICENSE.txt</license>
<authorEmail>admin@joomla.org</authorEmail>
<authorUrl>www.joomla.org</authorUrl>
<version>2.5.0</version>
<description>PLG_USER_PROFILE7_XML_DESCRIPTION</description>

<files>
<filename plugin="profile7">profile7.php</filename>
<filename>index.html</filename>
<folder>profiles</folder>
</files>
<languages>
<language tag="en-GB">en-GB.plg_user_profile7.ini</language>
<language tag="en-GB">en-GB.plg_user_profile7.sys.ini</language>
</languages>
<config>
<fields name="params">

<fieldset name="basic">
<field name="register-require-user" type="spacer" class="text"
label="PLG_USER_PROFILE7_FIELD_NAME_REGISTER_REQUIRE_USER"
/>

<field name="register-require_address1" type="list"

description="PLG_USER_PROFILE7_FIELD_ADDRESS1_DESC"
label="PLG_USER_PROFILE7_FIELD_ADDRESS1_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_address2" type="list"

description="PLG_USER_PROFILE7_FIELD_ADDRESS2_DESC"
label="PLG_USER_PROFILE7_FIELD_ADDRESS2_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_city" type="list"

description="PLG_USER_PROFILE7_FIELD_CITY_DESC"
label="PLG_USER_PROFILE7_FIELD_CITY_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_region" type="list"

description="PLG_USER_PROFILE7_FIELD_REGION_DESC"
label="PLG_USER_PROFILE7_FIELD_REGION_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_country" type="list"

description="PLG_USER_PROFILE7_FIELD_COUNTRY_DESC"
label="PLG_USER_PROFILE7_FIELD_COUNTRY_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_postal_code" type="list"

description="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_DESC"
label="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_phone" type="list"

description="PLG_USER_PROFILE7_FIELD_PHONE_DESC"
label="PLG_USER_PROFILE7_FIELD_PHONE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="register-require_website" type="list"

description="PLG_USER_PROFILE7_FIELD_WEB_SITE_DESC"
label="PLG_USER_PROFILE7_FIELD_WEB_SITE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field name="register-require_favoritebook"
type="list"

label="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_LABEL"
description="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_DESC"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field
name="register-require_aboutme"
type="list"

label="PLG_USER_PROFILE7_FIELD_ABOUT_ME_LABEL"
description="PLG_USER_PROFILE7_FIELD_ABOUT_ME_DESC"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="register-require_tos"
type="list"

label="PLG_USER_PROFILE7_FIELD_TOS_LABEL"
description="PLG_USER_PROFILE7_FIELD_TOS_DESC"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="register-require_subscribe"
type="list"

label="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_LABEL"
description="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="register-require_dob"
type="list"

label="PLG_USER_PROFILE7_FIELD_DOB_LABEL"
description="PLG_USER_PROFILE7_FIELD_DOB_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="spacer1" type="spacer"
hr="true"
/>
<field name="profile-require-user" type="spacer" class="text"
label="PLG_USER_PROFILE7_FIELD_NAME_PROFILE_REQUIRE_USER"
/>

<field name="profile-require_address1" type="list"

description="PLG_USER_PROFILE7_FIELD_ADDRESS1_DESC"
label="PLG_USER_PROFILE7_FIELD_ADDRESS1_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_address2" type="list"

description="PLG_USER_PROFILE7_FIELD_ADDRESS2_DESC"
label="PLG_USER_PROFILE7_FIELD_ADDRESS2_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_city" type="list"

description="PLG_USER_PROFILE7_FIELD_CITY_DESC"
label="PLG_USER_PROFILE7_FIELD_CITY_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_region" type="list"

description="PLG_USER_PROFILE7_FIELD_REGION_DESC"
label="PLG_USER_PROFILE7_FIELD_REGION_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_country" type="list"

description="PLG_USER_PROFILE7_FIELD_COUNTRY_DESC"
label="PLG_USER_PROFILE7_FIELD_COUNTRY_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_postal_code" type="list"

description="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_DESC"
label="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_phone" type="list"

description="PLG_USER_PROFILE7_FIELD_PHONE_DESC"
label="PLG_USER_PROFILE7_FIELD_PHONE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field name="profile-require_website" type="list"

description="PLG_USER_PROFILE7_FIELD_WEB_SITE_DESC"
label="PLG_USER_PROFILE7_FIELD_WEB_SITE_LABEL"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field name="profile-require_favoritebook"
type="list"

label="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_LABEL"
description="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>

<field
name="profile-require_aboutme"
type="list"

label="PLG_USER_PROFILE7_FIELD_ABOUT_ME_LABEL"
description="PLG_USER_PROFILE7_FIELD_ABOUT_ME_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="profile-require_tos"
type="list"

label="PLG_USER_PROFILE7_FIELD_TOS_LABEL"
description="PLG_USER_PROFILE7_FIELD_TOS_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="profile-require_dob"
type="list"

label="PLG_USER_PROFILE7_FIELD_DOB_LABEL"
description="PLG_USER_PROFILE7_FIELD_DOB_DESC"
>
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
<field
name="profile-require_subscribe"
type="list"

label="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_LABEL"
description="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_DESC">
<option value="2">JOPTION_REQUIRED</option>
<option value="1">JOPTION_OPTIONAL</option>
<option value="0">JDISABLED</option>
</field>
</fieldset>

</fields>
</config>
</extension>

--------------------------------------------------------------------------------------------------------------

--------------------------------------------------------------------------------------------------------------
<?xml version="1.0" encoding="utf-8"?>
<form>
<fields name="profile7">
<fieldset name="profile7"
label="PLG_USER_PROFILE7_SLIDER_LABEL"
>
<field
name="address1"
type="text"
id="address1"
description="PLG_USER_PROFILE7_FIELD_ADDRESS1_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_ADDRESS1_LABEL"
message="PLG_USER_PROFILE7_FIELD_ADDRESS1_MESSAGE"
size="30"
/>

<field
name="address2"
type="text"
id="address2"
description="PLG_USER_PROFILE7_FIELD_ADDRESS2_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_ADDRESS2_LABEL"
message="PLG_USER_PROFILE7_FIELD_ADDRESS1_MESSAGE"
size="30"
/>

<field
name="city"
type="text"
id="city"
description="PLG_USER_PROFILE7_FIELD_CITY_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_CITY_LABEL"
message="PLG_USER_PROFILE7_FIELD_CITY_MESSAGE"
size="30"
/>

<field
name="region"
type="text"
id="region"
description="PLG_USER_PROFILE7_FIELD_REGION_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_REGION_LABEL"
message="PLG_USER_PROFILE7_FIELD_REGION_MESSAGE"
size="30"
/>

<field
name="country"
type="text"
id="country"
description="PLG_USER_PROFILE7_FIELD_COUNTRY_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_COUNTRY_LABEL"
message="PLG_USER_PROFILE7_FIELD_COUNTRY_MESSAGE"
size="30"
/>

<field
name="postal_code"
type="text"
id="postal_code"
description="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_LABEL"
message="PLG_USER_PROFILE7_FIELD_POSTAL_CODE_MESSAGE"
size="30"
/>

<field
name="phone"
type="tel"
id="phone"
description="PLG_USER_PROFILE7_FIELD_PHONE_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_PHONE_LABEL"
message="PLG_USER_PROFILE7_FIELD_PHONE_MESSAGE"
size="30"
/>

<field
name="website"
type="url"
id="website"
description="PLG_USER_PROFILE7_FIELD_WEB_SITE_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_WEB_SITE_LABEL"
message="PLG_USER_PROFILE7_FIELD_WEB_SITE_MESSAGE"
size="30"
/>
<field
name="favoritebook"
type="text"
description="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_DESC"
filter="string"
label="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_LABEL"
message="PLG_USER_PROFILE7_FIELD_FAVORITE_BOOK_MESSAGE"
size="30"
/>
<field
name="aboutme"
type="textarea"
description="PLG_USER_PROFILE7_FIELD_ABOUT_ME_DESC"
label="PLG_USER_PROFILE7_FIELD_ABOUT_ME_LABEL"
message="PLG_USER_PROFILE7_FIELD_ABOUT_ME_MESSAGE"
cols="30"
rows="5"
filter="safehtml"
/>
<field
name="subscribe"
type="radio"
default="0"
label="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_LABEL"
description="PLG_USER_PROFILE7_FIELD_SUBSCRIBE_DESC">
<option value="0">PLG_USER_PROFILE7_OPTION_NO</option>
<option value="1">PLG_USER_PROFILE7_OPTION_YES</option>
</field>
<field
name="tos"
type="radio"
label="PLG_USER_PROFILE7_FIELD_TOS_LABEL"
description="PLG_USER_PROFILE7_FIELD_TOS_DESC">
<option value="1">PLG_USER_PROFILE7_OPTION_AGREE</option>
</field>

<field
name="dob"
type="calendar"
label="PLG_USER_PROFILE7_FIELD_DOB_LABEL"
description="PLG_USER_PROFILE7_FIELD_DOB_DESC">
</field>
</fieldset>
</fields>
</form>

------------------------------------------------------------------------------------------------------------