diff --git a/.classpath b/.classpath index d97562f..a25b393 100644 --- a/.classpath +++ b/.classpath @@ -23,27 +23,7 @@ - - - - - - - - - - - - - - - - - - - - - + @@ -53,7 +33,32 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/old_widget/Entry.cpp b/old_widget/Entry.cpp deleted file mode 100644 index 17b5893..0000000 --- a/old_widget/Entry.cpp +++ /dev/null @@ -1,612 +0,0 @@ -/** @file - * @author Edouard DUPIN - * @copyright 2011, Edouard DUPIN, all right reserved - * @license MPL v2.0 (see license file) - */ - -#include -#include -#include -#include -#include -#include -#include -ETK_DECLARE_TYPE(ewol::widget::Entry); - -// DEFINE for the shader display system : -#define STATUS_NORMAL (0) -#define STATUS_HOVER (1) -#define STATUS_SELECTED (2) - -ewol::widget::Entry::Entry() : - signalClick(this, "click", "the user Click on the Entry box"), - signalEnter(this, "enter", "The cursor enter inside the button"), - signalModify(this, "modify", "Entry box value change"), - propertyPassword(this, "password", - false, - "Not display content in password mode", - ewol::widget::Entry::onChangePropertyPassword), - propertyShape(this, "shape", - etk::Uri("THEME_GUI:///Entry.json?lib=ewol"), - "Shaper to display the background", - ewol::widget::Entry::onChangePropertyShaper), - propertyValue(this, "value", - "", - "Value display in the entry (decorated text)", - ewol::widget::Entry::onChangePropertyValue), - propertyMaxCharacter(this, "max", - 0x7FFFFFFF, 0, 0x7FFFFFFF, - "Maximum char that can be set on the Entry", - ewol::widget::Entry::onChangePropertyMaxCharacter), - propertyRegex(this, "regex", - ".*", - "Control what it is write with a regular expression", - ewol::widget::Entry::onChangePropertyRegex), - propertyTextWhenNothing(this, "empty-text", - "", - "Text when nothing is written", - ewol::widget::Entry::onChangePropertyTextWhenNothing), - this.needUpdateTextPos(true), - this.displayStartPosition(0), - this.displayCursor(false), - this.displayCursorPos(0), - this.displayCursorPosSelection(0) { - addObjectType("ewol::widget::Entry"); - propertyCanFocus.setDirectCheck(true); -} - -void ewol::widget::Entry::init() { - Widget::init(); - propertyShape.notifyChange(); - - this.regex.compile(propertyRegex.get()); - if (this.regex.getStatus() == false) { - Log.error("can not parse regex for : " + propertyRegex); - } - markToRedraw(); - - shortCutAdd("ctrl+w", "clean"); - shortCutAdd("ctrl+x", "cut"); - shortCutAdd("ctrl+c", "copy"); - shortCutAdd("ctrl+v", "paste"); - shortCutAdd("ctrl+a", "select:all"); - shortCutAdd("ctrl+shift+a", "select:none"); - signalShortcut.connect(sharedFromThis(), ewol::widget::Entry::onCallbackShortCut); -} - - -ewol::widget::Entry::~Entry() { - -} - -void ewol::widget::Entry::onCallbackShortCut( String _value) { - if (_value == "clean") { - onCallbackEntryClean(); - } else if (_value == "cut") { - onCallbackCut(); - } else if (_value == "copy") { - onCallbackCopy(); - } else if (_value == "paste") { - Log.warning("Request past ..."); - onCallbackPaste(); - } else if (_value == "select:all") { - onCallbackSelect(true); - } else if (_value == "select:none") { - onCallbackSelect(false); - } else { - Log.warning("Unknow event from ShortCut : " + _value); - } -} - -void ewol::widget::Entry::calculateMinMaxSize() { - // call main class - Widget::calculateMinMaxSize(); - // get generic padding - ewol::Padding padding = this.shaper.getPadding(); - int minHeight = this.text.calculateSize(Character('A')).y(); - Vector2f minimumSizeBase(20, minHeight); - // add padding : - minimumSizeBase += Vector2f(padding.x(), padding.y()); - this.minSize.setMax(minimumSizeBase); - // verify the min max of the min size ... - checkMinSize(); -} - - -void ewol::widget::Entry::onDraw() { - this.shaper.draw(); - this.text.draw(); -} - - -void ewol::widget::Entry::onRegenerateDisplay() { - if (needRedraw() == true) { - this.shaper.clear(); - this.text.clear(); - if (this.colorIdTextFg >= 0) { - this.text.setDefaultColorFg(this.shaper.getColor(this.colorIdTextFg)); - this.text.setDefaultColorBg(this.shaper.getColor(this.colorIdTextBg)); - this.text.setCursorColor(this.shaper.getColor(this.colorIdCursor)); - this.text.setSelectionColor(this.shaper.getColor(this.colorIdSelection)); - } - updateTextPosition(); - ewol::Padding padding = this.shaper.getPadding(); - - Vector2f tmpSizeShaper = this.minSize; - if (propertyFill.x() == true) { - tmpSizeShaper.setX(this.size.x()); - } - if (propertyFill.y() == true) { - tmpSizeShaper.setY(this.size.y()); - } - - Vector2f tmpOriginShaper = (this.size - tmpSizeShaper) / 2.0f; - Vector2f tmpSizeText = tmpSizeShaper - Vector2f(padding.x(), padding.y()); - Vector2f tmpOriginText = (this.size - tmpSizeText) / 2.0f; - // sometimes, the user define an height bigger than the real size needed == > in this case we need to center the text in the shaper ... - int minHeight = this.text.calculateSize(Character('A')).y(); - if (tmpSizeText.y() > minHeight) { - tmpOriginText += Vector2f(0,(tmpSizeText.y()-minHeight)/2.0f); - } - // fix all the position in the int class: - tmpSizeShaper = Vector2fClipInt32(tmpSizeShaper); - tmpOriginShaper = Vector2fClipInt32(tmpOriginShaper); - tmpSizeText = Vector2fClipInt32(tmpSizeText); - tmpOriginText = Vector2fClipInt32(tmpOriginText); - - this.text.reset(); - this.text.setClippingWidth(tmpOriginText, tmpSizeText); - this.text.setPos(tmpOriginText+Vector2f(this.displayStartPosition,0)); - if (this.displayCursorPosSelection != this.displayCursorPos) { - this.text.setCursorSelection(this.displayCursorPos, this.displayCursorPosSelection); - } else { - this.text.setCursorPos(this.displayCursorPos); - } - etk::UString valueToDisplay = etk::toUString(*propertyValue); - if (*propertyPassword == true) { - for (auto it: valueToDisplay) { - it = '*'; - } - } - - if (valueToDisplay.size() != 0) { - this.text.print(valueToDisplay); - } else { - if (propertyTextWhenNothing.size() != 0) { - this.text.printDecorated(propertyTextWhenNothing); - } - } - this.text.setClippingMode(false); - - this.shaper.setShape(tmpOriginShaper, tmpSizeShaper, tmpOriginText, tmpSizeText); - } -} - - -void ewol::widget::Entry::updateCursorPosition( Vector2f _pos, boolean _selection) { - ewol::Padding padding = this.shaper.getPadding(); - - Vector2f relPos = relativePosition(_pos); - relPos.setX(relPos.x()-this.displayStartPosition - padding.xLeft()); - // try to find the new cursor position : - String tmpDisplay = String(propertyValue, 0, this.displayStartPosition); - int displayHidenSize = this.text.calculateSize(tmpDisplay).x(); - //Log.debug("hidenSize : " + displayHidenSize); - int newCursorPosition = -1; - int tmpTextOriginX = padding.xLeft(); - for (int iii=0; iii= relPos.x()-tmpTextOriginX) { - newCursorPosition = iii; - break; - } - } - if (newCursorPosition == -1) { - newCursorPosition = propertyValue.size(); - } - if (_selection == false) { - this.displayCursorPos = newCursorPosition; - this.displayCursorPosSelection = this.displayCursorPos; - markToRedraw(); - } else { - if (this.displayCursorPos == this.displayCursorPosSelection) { - this.displayCursorPosSelection = this.displayCursorPos; - } - this.displayCursorPos = newCursorPosition; - markToRedraw(); - } - markToUpdateTextPosition(); -} - - -void ewol::widget::Entry::removeSelected() { - if (this.displayCursorPosSelection == this.displayCursorPos) { - // nothing to cut ... - return; - } - int pos1 = this.displayCursorPosSelection; - int pos2 = this.displayCursorPos; - if(this.displayCursorPosSelection>this.displayCursorPos) { - pos2 = this.displayCursorPosSelection; - pos1 = this.displayCursorPos; - } - // remove data ... - this.displayCursorPos = pos1; - this.displayCursorPosSelection = pos1; - propertyValue.getDirect().erase(pos1, pos2-pos1); - markToRedraw(); -} - - -void ewol::widget::Entry::copySelectionToClipBoard(enum gale::context::clipBoard::clipboardListe _clipboardID) { - if (this.displayCursorPosSelection == this.displayCursorPos) { - // nothing to cut ... - return; - } - int pos1 = this.displayCursorPosSelection; - int pos2 = this.displayCursorPos; - if(this.displayCursorPosSelection>this.displayCursorPos) { - pos2 = this.displayCursorPosSelection; - pos1 = this.displayCursorPos; - } - // Copy - String tmpData = String(propertyValue, pos1, pos2); - gale::context::clipBoard::set(_clipboardID, tmpData); -} - - -boolean ewol::widget::Entry::onEventInput( ewol::event::Input _event) { - Log.warning("Event on Input ... " + _event); - if (_event.getId() == 1) { - if (KeyStatus::pressSingle == _event.getStatus()) { - keepFocus(); - signalClick.emit(); - //nothing to do ... - return true; - } else if (KeyStatus::pressDouble == _event.getStatus()) { - keepFocus(); - // select word - this.displayCursorPosSelection = this.displayCursorPos-1; - // search forward - for (int iii=this.displayCursorPos; iii <= propertyValue.size(); iii++) { - if(iii == propertyValue.size()) { - this.displayCursorPos = iii; - break; - } - if(!( ( propertyValue.get()[iii] >= 'a' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= 'z') - || ( propertyValue.get()[iii] >= 'A' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= 'Z') - || ( propertyValue.get()[iii] >= '0' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= '9') - || propertyValue.get()[iii] == '_' - || propertyValue.get()[iii] == '-' - ) ) { - this.displayCursorPos = iii; - break; - } - } - // search backward - for (long iii=this.displayCursorPosSelection; iii >= -1; iii--) { - if(iii == -1) { - this.displayCursorPosSelection = 0; - break; - } - if(!( ( propertyValue.get()[iii] >= 'a' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= 'z') - || ( propertyValue.get()[iii] >= 'A' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= 'Z') - || ( propertyValue.get()[iii] >= '0' - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM propertyValue.get()[iii] <= '9') - || propertyValue.get()[iii] == '_' - || propertyValue.get()[iii] == '-' - ) ) { - this.displayCursorPosSelection = iii+1; - break; - } - } - // Copy to clipboard Middle ... - copySelectionToClipBoard(gale::context::clipBoard::clipboardSelection); - markToRedraw(); - } else if (KeyStatus::pressTriple == _event.getStatus()) { - keepFocus(); - this.displayCursorPosSelection = 0; - this.displayCursorPos = propertyValue.size(); - } else if (KeyStatus::down == _event.getStatus()) { - keepFocus(); - updateCursorPosition(_event.getPos()); - markToRedraw(); - } else if (KeyStatus::move == _event.getStatus()) { - keepFocus(); - updateCursorPosition(_event.getPos(), true); - markToRedraw(); - } else if (KeyStatus::up == _event.getStatus()) { - keepFocus(); - updateCursorPosition(_event.getPos(), true); - // Copy to clipboard Middle ... - copySelectionToClipBoard(gale::context::clipBoard::clipboardSelection); - markToRedraw(); - } - } - else if( KeyType::mouse == _event.getType() - LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM _event.getId() == 2) { - if( _event.getStatus() == KeyStatus::down - || _event.getStatus() == KeyStatus::move - || _event.getStatus() == KeyStatus::up) { - keepFocus(); - // updatethe cursor position : - updateCursorPosition(_event.getPos()); - } - // Paste current selection only when up button - if (_event.getStatus() == KeyStatus::up) { - keepFocus(); - // middle button => past data... - gale::context::clipBoard::request(gale::context::clipBoard::clipboardSelection); - } - } - return false; -} - - -boolean ewol::widget::Entry::onEventEntry( ewol::event::Entry _event) { - Log.warning("Event on Entry ... " + _event); - if (_event.getType() == KeyKeyboard::character) { - if(_event.getStatus() == KeyStatus::down) { - // remove curent selected data ... - removeSelected(); - if( _event.getChar() == '\n' - || _event.getChar() == '\r') { - signalEnter.emit(propertyValue); - return true; - } else if (_event.getChar() == 0x7F) { - // SUPPR : - if (propertyValue.size() > 0 LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM this.displayCursorPos < (long)propertyValue.size()) { - propertyValue.getDirect().erase(this.displayCursorPos, 1); - this.displayCursorPos = etk::max(this.displayCursorPos, 0); - this.displayCursorPosSelection = this.displayCursorPos; - } - } else if (_event.getChar() == 0x08) { - // DEL : - if (propertyValue.size() > 0 LOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOMLOM this.displayCursorPos != 0) { - propertyValue.getDirect().erase(this.displayCursorPos-1, 1); - this.displayCursorPos--; - this.displayCursorPos = etk::max(this.displayCursorPos, 0); - this.displayCursorPosSelection = this.displayCursorPos; - } - } else if(_event.getChar() >= 20) { - Log.error("get data: '" + _event.getChar() + "' = '" + u32char::convertToUtf8(_event.getChar()) + "'"); - if ((long)propertyValue.size() > propertyMaxCharacter) { - Log.info("Reject data for entry : '" + _event.getChar() + "'"); - } else { - String newData = propertyValue; - String inputData = u32char::convertToUtf8(_event.getChar()); - newData.insert(newData.begin()+this.displayCursorPos, inputData); - setInternalValue(newData); - if (propertyValue.get() == newData) { - this.displayCursorPos += inputData.size(); - this.displayCursorPosSelection = this.displayCursorPos; - } - } - } - signalModify.emit(propertyValue); - markToRedraw(); - return true; - } - return false; - } else { - if(_event.getStatus() == KeyStatus::down) { - switch (_event.getType()) { - case KeyKeyboard::left: - this.displayCursorPos--; - break; - case KeyKeyboard::right: - this.displayCursorPos++; - break; - case KeyKeyboard::start: - this.displayCursorPos = 0; - break; - case KeyKeyboard::end: - this.displayCursorPos = propertyValue.size(); - break; - default: - return false; - } - this.displayCursorPos = etk::avg(0, this.displayCursorPos, (int)propertyValue.size()); - this.displayCursorPosSelection = this.displayCursorPos; - markToRedraw(); - return true; - } - } - return false; -} - -void ewol::widget::Entry::setInternalValue( String _newData) { - String previous = propertyValue; - // check the RegExp : - if (_newData.size()>0) { - /* - if (this.regex.parse(_newData, 0, _newData.size()) == false) { - Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "'" ); - return; - } - if (this.regex.start() != 0) { - Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "' (start position error)" ); - return; - } - if (this.regex.stop() != _newData.size()) { - Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "' (stop position error)" ); - return; - } - */ - } - propertyValue.setDirect(_newData); - markToRedraw(); -} - -void ewol::widget::Entry::onEventClipboard(enum gale::context::clipBoard::clipboardListe _clipboardID) { - // remove curent selected data ... - removeSelected(); - // get current selection / Copy : - String tmpData = get(_clipboardID); - // add it on the current display : - if (tmpData.size() != 0) { - String newData = propertyValue; - newData.insert(this.displayCursorPos, tmpData[0]); - setInternalValue(newData); - if (propertyValue.get() == newData) { - if (propertyValue.size() == tmpData.size()) { - this.displayCursorPos = tmpData.size(); - } else { - this.displayCursorPos += tmpData.size(); - } - this.displayCursorPosSelection = this.displayCursorPos; - markToRedraw(); - } - } - signalModify.emit(propertyValue); -} - -void ewol::widget::Entry::onCallbackEntryClean() { - propertyValue.setDirect(""); - this.displayStartPosition = 0; - this.displayCursorPos = 0; - this.displayCursorPosSelection = this.displayCursorPos; - markToRedraw(); -} - -void ewol::widget::Entry::onCallbackCut() { - copySelectionToClipBoard(gale::context::clipBoard::clipboardStd); - removeSelected(); - signalModify.emit(propertyValue); -} - -void ewol::widget::Entry::onCallbackCopy() { - copySelectionToClipBoard(gale::context::clipBoard::clipboardStd); -} - -void ewol::widget::Entry::onCallbackPaste() { - gale::context::clipBoard::request(gale::context::clipBoard::clipboardStd); -} - -void ewol::widget::Entry::onCallbackSelect(boolean _all) { - if(_all == true) { - this.displayCursorPosSelection = 0; - this.displayCursorPos = propertyValue.size(); - } else { - this.displayCursorPosSelection = this.displayCursorPos; - } - markToRedraw(); -} - -void ewol::widget::Entry::markToUpdateTextPosition() { - this.needUpdateTextPos = true; -} - -void ewol::widget::Entry::updateTextPosition() { - if (this.needUpdateTextPos == false) { - return; - } - ewol::Padding padding = this.shaper.getPadding(); - - int tmpSizeX = this.minSize.x(); - if (propertyFill.x() == true) { - tmpSizeX = this.size.x(); - } - int tmpUserSize = tmpSizeX - padding.x(); - int totalWidth = this.text.calculateSize(propertyValue).x(); - // Check if the data inside the display can be contain in the entry box - if (totalWidth < tmpUserSize) { - // all can be display : - this.displayStartPosition = 0; - } else { - // all can not be set : - String tmpDisplay = String(propertyValue, 0, this.displayCursorPos); - int pixelCursorPos = this.text.calculateSize(tmpDisplay).x(); - // check if the Cussor is visible at 10px nearest the border : - int tmp1 = pixelCursorPos+this.displayStartPosition; - Log.debug("cursorPos=" + pixelCursorPos + "px maxSize=" + tmpUserSize + "px tmp1=" + tmp1); - if (tmp1<10) { - // set the cursor on le left - this.displayStartPosition = etk::min(-pixelCursorPos+10, 0); - } else if (tmp1>tmpUserSize-10) { - // set the cursor of the Right - this.displayStartPosition = etk::min(-pixelCursorPos + tmpUserSize - 10, 0); - } - // else : the cursor is inside the display - //this.displayStartPosition = -totalWidth + tmpUserSize; - } -} - -void ewol::widget::Entry::onGetFocus() { - this.displayCursor = true; - changeStatusIn(STATUS_SELECTED); - showKeyboard(); - markToRedraw(); -} - -void ewol::widget::Entry::onLostFocus() { - this.displayCursor = false; - changeStatusIn(STATUS_NORMAL); - hideKeyboard(); - markToRedraw(); -} - -void ewol::widget::Entry::changeStatusIn(int _newStatusId) { - if (this.shaper.changeStatusIn(_newStatusId) == true) { - this.PCH = getObjectManager().periodicCall.connect(this, ewol::widget::Entry::periodicCall); - markToRedraw(); - } -} - -void ewol::widget::Entry::periodicCall( ewol::event::Time _event) { - if (this.shaper.periodicCall(_event) == false) { - this.PCH.disconnect(); - } - markToRedraw(); -} - -void ewol::widget::Entry::onChangePropertyPassword() { - markToRedraw(); -} - -void ewol::widget::Entry::onChangePropertyShaper() { - this.shaper.setSource(propertyShape.get()); - this.colorIdTextFg = this.shaper.requestColor("text-foreground"); - this.colorIdTextBg = this.shaper.requestColor("text-background"); - this.colorIdCursor = this.shaper.requestColor("text-cursor"); - this.colorIdSelection = this.shaper.requestColor("text-selection"); -} - -void ewol::widget::Entry::onChangePropertyValue() { - String newData = propertyValue.get(); - if ((long)newData.size() > propertyMaxCharacter) { - newData = String(newData, 0, propertyMaxCharacter); - Log.debug("Limit entry set of data... " + String(newData, propertyMaxCharacter)); - } - // set the value with the check of the RegExp ... - setInternalValue(newData); - if (newData == propertyValue.get()) { - this.displayCursorPos = propertyValue.size(); - this.displayCursorPosSelection = this.displayCursorPos; - Log.verbose("Set : '" + newData + "'"); - } - markToRedraw(); -} - -void ewol::widget::Entry::onChangePropertyMaxCharacter() { - // TODO : check nomber of char in the data -} - -void ewol::widget::Entry::onChangePropertyRegex() { - this.regex.compile(propertyRegex.get()); - if (this.regex.getStatus() == false) { - Log.error("can not parse regex for : " + propertyRegex); - } - markToRedraw(); -} - -void ewol::widget::Entry::onChangePropertyTextWhenNothing() { - markToRedraw(); -} - diff --git a/old_widget/Entry.java b/old_widget/Entry.java deleted file mode 100644 index cb5bbd0..0000000 --- a/old_widget/Entry.java +++ /dev/null @@ -1,141 +0,0 @@ -/** @file - * @author Edouard DUPIN - * @copyright 2011, Edouard DUPIN, all right reserved - * @license MPL v2.0 (see license file) - */ -#pragma once - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -namespace ewol { - namespace widget { - class Entry; - using Entry = ememory::Ptr; - using EntryWeak = ememory::WeakPtr; - /** - * @ingroup ewolWidgetGroup - * Entry box display : - * - * ~~~~~~~~~~~~~~~~~~~~~~ - * ---------------------------------------------- - * | Editable Text | - * ---------------------------------------------- - * ~~~~~~~~~~~~~~~~~~~~~~ - */ - class Entry : public Widget { - public: // Event list - esignal::Signal<> signalClick; //!< bang on click the entry box - esignal::Signal signalEnter; //!< Enter key is pressed - esignal::Signal signalModify; //!< data change - public: // propertie list - eproperty::Value propertyPassword; //!< Disable display of the content of the entry - eproperty::Value propertyShape; - eproperty::Value propertyValue; //!< string that must be displayed - eproperty::Range propertyMaxCharacter; //!< number max of xharacter in the list - eproperty::Value propertyRegex; //!< regular expression value - eproperty::Value propertyTextWhenNothing; //!< Text to display when nothing in in the entry (decorated text...) - private: - ewol::compositing::Shaper this.shaper; - int this.colorIdTextFg; //!< color property of the text foreground - int this.colorIdTextBg; //!< color property of the text background - int this.colorIdCursor; //!< color property of the text cursor - int this.colorIdSelection; //!< color property of the text selection - ewol::compositing::Text this.text; //!< text display this.text - protected: - /** - * Contuctor - * @param _newData The USting that might be set in the Entry box (no event generation!!) - */ - Entry(); - void init() ; - public: - DECLARE_WIDGET_FACTORY(Entry, "Entry"); - /** - * Destuctor - */ - ~Entry(); - protected: - /** - * internal check the value with RegExp checking - * @param _newData The new string to display - */ - void setInternalValue( String _newData); - private: - etk::RegEx this.regex; //!< regular expression to check content - private: - boolean this.needUpdateTextPos; //!< text position can have change - int this.displayStartPosition; //!< ofset in pixel of the display of the UString - boolean this.displayCursor; //!< Cursor must be display only when the widget has the focus - int this.displayCursorPos; //!< Cursor position in number of Char - int this.displayCursorPosSelection; //!< Selection position end (can be befor or after cursor and == this.displayCursorPos chan no selection availlable - protected: - /** - * informe the system thet the text change and the start position change - */ - void markToUpdateTextPosition(); - /** - * update the display position start == > depending of the position of the Cursor and the size of the Data inside - * @change this.displayStartPosition < == updated - */ - void updateTextPosition(); - /** - * change the cursor position with the curent position requested on the display - * @param _pos Absolute position of the event - * @note The display is automaticly requested when change apear. - */ - void updateCursorPosition( Vector2f _pos, boolean _Selection=false); - public: - /** - * Copy the selected data on the specify clipboard - * @param _clipboardID Selected clipboard - */ - void copySelectionToClipBoard(enum gale::context::clipBoard::clipboardListe _clipboardID); - /** - * remove the selected area - * @note This request a regeneration of the display - */ - void removeSelected(); - public: - void onRegenerateDisplay() ; - boolean onEventInput( ewol::event::Input _event) ; - boolean onEventEntry( ewol::event::Entry _event) ; - void onEventClipboard(enum gale::context::clipBoard::clipboardListe _clipboardID) ; - void calculateMinMaxSize() ; - protected: - void onDraw() ; - void onGetFocus() ; - void onLostFocus() ; - void changeStatusIn(int _newStatusId); - protected: - esignal::Connection this.PCH; //!< Periodic call handle to remove it when needed - /** - * Periodic call to update grapgic display - * @param _event Time generic event - */ - void periodicCall( ewol::event::Time _event); - private: // callback functions - void onCallbackShortCut( String _value); - void onCallbackEntryClean(); - void onCallbackCut(); - void onCallbackCopy(); - void onCallbackPaste(); - void onCallbackSelect(boolean _all); - protected: - void onChangePropertyPassword(); - void onChangePropertyShaper(); - void onChangePropertyValue(); - void onChangePropertyMaxCharacter(); - void onChangePropertyRegex(); - void onChangePropertyTextWhenNothing(); - }; - }; -}; diff --git a/resources/resources/ewol/data/color3.vert b/resources/resources/ewol/data/color3.vert index 5134b3b..c71c43e 100644 --- a/resources/resources/ewol/data/color3.vert +++ b/resources/resources/ewol/data/color3.vert @@ -8,15 +8,13 @@ precision mediump int; // Input : layout (location = 0) in vec3 in_position; layout (location = 3) in vec4 in_colors; -uniform mat4 in_MatrixTransformation; -uniform mat4 in_MatrixPosition; - +uniform mat4 in_matrixTransformation; +uniform mat4 in_matrixProjection; +uniform mat4 in_matrixView; // output : varying vec4 io_color; void main(void) { - gl_Position = in_MatrixTransformation * in_MatrixPosition * vec4(in_position, 1.0); - gl_Position = in_MatrixTransformation * vec4(in_position, 1.0); - //gl_Position = vec4(in_position, 1.0); + gl_Position = in_matrixProjection * in_matrixView * in_matrixTransformation * vec4(in_position, 1.0); io_color = in_colors; } diff --git a/resources/resources/ewol/data/text.vert b/resources/resources/ewol/data/text.vert index 80c5212..740b2f4 100644 --- a/resources/resources/ewol/data/text.vert +++ b/resources/resources/ewol/data/text.vert @@ -9,7 +9,9 @@ precision mediump int; layout (location = 0) in vec3 in_position; layout (location = 1) in vec2 in_textureCoords; layout (location = 3) in vec4 in_colors; -uniform mat4 in_MatrixTransformation; +uniform mat4 in_matrixTransformation; +uniform mat4 in_matrixProjection; +uniform mat4 in_matrixView; // output : varying vec4 io_color; @@ -26,8 +28,7 @@ void main(void) { */ varying vec4 io_patern; void main(void) { - gl_Position = in_MatrixTransformation * vec4(in_position, 1.0); - //gl_Position = gl_ProjectionMatrix * gl_ModelViewMatrix * vec4(in_coord2d, 0.0, 1.0); + gl_Position = in_matrixProjection * in_matrixView * in_matrixTransformation * vec4(in_position, 1.0); // set output color : io_color = in_colors; if (in_textureCoords.x<1.0) { diff --git a/resources/resources/ewol/theme/shape/Button.json b/resources/resources/ewol/theme/shape/Button.json index b2a5ce8..a50972f 100644 --- a/resources/resources/ewol/theme/shape/Button.json +++ b/resources/resources/ewol/theme/shape/Button.json @@ -1,7 +1,4 @@ { - mode:2, - display-outside:false, - padding-out-left:1, padding-out-right:1, padding-out-top:1, @@ -17,7 +14,6 @@ padding-in-top:1, padding-in-buttom:1, - change-time:356, - program:"THEME_GUI:///Button.prog?lib=ewol", - color:"THEME_COLOR:///Button.json?lib=ewol" + object-file:"THEME:///Button.obj?lib=ewol", + object-size:"1,1,1" } diff --git a/resources/resources/ewol/theme/shape/Entry.blend b/resources/resources/ewol/theme/shape/Entry.blend new file mode 100644 index 0000000..d46e150 Binary files /dev/null and b/resources/resources/ewol/theme/shape/Entry.blend differ diff --git a/resources/resources/ewol/theme/shape/Entry.blend1 b/resources/resources/ewol/theme/shape/Entry.blend1 new file mode 100644 index 0000000..facffdf Binary files /dev/null and b/resources/resources/ewol/theme/shape/Entry.blend1 differ diff --git a/resources/resources/ewol/theme/shape/Entry.emf b/resources/resources/ewol/theme/shape/Entry.emf new file mode 100644 index 0000000..b60b908 --- /dev/null +++ b/resources/resources/ewol/theme/shape/Entry.emf @@ -0,0 +1,2 @@ +EMF(STRING) +# Blender v2.92.0 EMF File: 'Entry.blend' diff --git a/resources/resources/ewol/theme/shape/Entry.frag b/resources/resources/ewol/theme/shape/Entry.frag deleted file mode 100644 index bf5d7f2..0000000 --- a/resources/resources/ewol/theme/shape/Entry.frag +++ /dev/null @@ -1,27 +0,0 @@ -#ifdef GL_ES -precision mediump float; -precision mediump int; -#endif - -uniform vec4 EW_background; -uniform vec4 EW_border; - - -// transmit from the vertex shader -varying vec2 v_position; // interpolated position ... -varying vec2 v_propPos; -varying vec4 v_colorTansition; - -void main(void) { - // prevent origin moving ... - gl_FragColor = vec4(v_propPos.y, v_propPos.x, 1.0, 1.0); - if( v_propPos.x == 1.0 - && v_propPos.y == 1.0) { - gl_FragColor = v_colorTansition; - } else if ( v_propPos.x == 0.0 - || v_propPos.y == 0.0) { - gl_FragColor = EW_background; - } else { - gl_FragColor = EW_border; - } -} \ No newline at end of file diff --git a/resources/resources/ewol/theme/shape/Entry.json b/resources/resources/ewol/theme/shape/Entry.json index 79eedd2..82f95f4 100644 --- a/resources/resources/ewol/theme/shape/Entry.json +++ b/resources/resources/ewol/theme/shape/Entry.json @@ -1,23 +1,25 @@ { - mode:2, - display-outside:false, - + # padding "outside" the object in pixel ==> prevent bad display padding-out-left:2, padding-out-right:2, padding-out-top:2, padding-out-buttom:2, - border-left:1, - border-right:1, - border-top:1, - border-buttom:1, - + # padding "inside" the object in piuxel ==> prevent bad display padding-in-left:2, padding-in-right:2, padding-in-top:2, padding-in-buttom:2, - change-time:356, - program:"THEME_GUI:///Entry.prog?lib=ewol", - color:"THEME_COLOR:///Entry.json?lib=ewol" + # render program: + program-vert:"THEME:shape/aaRenderShape.vert?lib=ewol", + program-frag:"THEME:shape/aaRenderShape.frag?lib=ewol", + + # Object to render (with modification) + object-file:"THEME:shape/Entry.obj?lib=ewol", + + # Theme Image (pallete) + image-palette:"THEME:shape/GuiPaletteColor.png?lib=ewol", + # read mode: 'nearest', 'linear' + image-palette-load-mode: "nearest", } diff --git a/resources/resources/ewol/theme/shape/Entry.mtl b/resources/resources/ewol/theme/shape/Entry.mtl new file mode 100644 index 0000000..4f7a6c4 --- /dev/null +++ b/resources/resources/ewol/theme/shape/Entry.mtl @@ -0,0 +1,24 @@ +# Blender MTL File: 'Entry.blend' +# Material Count: 2 + +newmtl TextArea +Ns 225.000000 +Ka 1.000000 1.000000 1.000000 +Kd 0.800000 0.800000 0.800000 +Ks 0.500000 0.500000 0.500000 +Ke 0.000000 0.000000 0.000000 +Ni 1.450000 +d 1.000000 +illum 2 +map_Kd empty_area.png + +newmtl center +Ns 225.000000 +Ka 1.000000 1.000000 1.000000 +Kd 0.800000 0.800000 0.800000 +Ks 0.500000 0.500000 0.500000 +Ke 0.000000 0.000000 0.000000 +Ni 1.450000 +d 1.000000 +illum 2 +map_Kd GuiPaletteColor.png diff --git a/resources/resources/ewol/theme/shape/Entry.obj b/resources/resources/ewol/theme/shape/Entry.obj new file mode 100644 index 0000000..62398b4 --- /dev/null +++ b/resources/resources/ewol/theme/shape/Entry.obj @@ -0,0 +1,99 @@ +# Blender v2.92.0 OBJ File: 'Entry.blend' +# www.blender.org +mtllib Entry.mtl +o Cube +v 20.042355 20.042355 -7.751226 +v 20.042355 -20.042355 -7.751226 +v 20.042355 20.042355 4.633502 +v 20.042355 -20.042355 4.633502 +v -20.042355 20.042355 -7.751226 +v -20.042355 -20.042355 -7.751226 +v -20.042355 20.042355 4.633502 +v -20.042355 -20.042355 4.633502 +v 10.127714 10.127714 7.726907 +v 10.127714 -10.127714 7.726907 +v -10.127714 10.127714 7.726907 +v -10.127714 -10.127714 7.726907 +v -10.127714 -10.127714 9.146553 +v -10.127714 10.127714 9.146553 +v 10.127714 10.127714 9.146553 +v 10.127714 -10.127714 9.146553 +vt 0.174907 0.947863 +vt 0.131613 0.991157 +vt 0.132843 0.945402 +vt 0.074219 0.995849 +vt 0.120606 0.943115 +vt 0.121582 0.993408 +vt 0.178368 0.944941 +vt 0.137534 0.984544 +vt 0.142456 0.948632 +vt 0.171985 0.949093 +vt 0.136074 0.991157 +vt 0.137304 0.950323 +vt 0.174677 0.949093 +vt 0.135074 0.992387 +vt 0.136304 0.949093 +vt 0.112927 0.992387 +vt 0.078245 0.948093 +vt 0.073324 0.991157 +vt 0.101769 0.970961 +vt 0.080974 0.959440 +vt 0.102023 0.957458 +vt 0.111927 0.985005 +vt 0.078476 0.953015 +vt 0.082167 0.983774 +vt 0.137534 0.988235 +vt 0.177138 0.947863 +vt 0.135074 0.947862 +vt 0.013265 0.951784 +vt 0.051868 0.992387 +vt 0.013034 0.993618 +vt 0.178598 0.993618 +vt 0.074219 0.944092 +vt 0.178368 0.988235 +vt 0.173216 0.991157 +vt 0.175907 0.989926 +vt 0.111696 0.944402 +vt 0.080720 0.975385 +vt 0.113157 0.949323 +vt 0.172446 0.988465 +vt 0.054098 0.951784 +vt 0.000100 0.000100 +vt 0.999900 0.999900 +vt 0.000100 0.999900 +vt 0.999900 0.000100 +vn 0.0000 1.0000 0.0000 +vn -0.2978 0.0000 0.9546 +vn -1.0000 0.0000 0.0000 +vn 0.0000 -1.0000 0.0000 +vn 1.0000 0.0000 0.0000 +vn 0.0000 -0.2978 0.9546 +vn 0.0000 0.2978 0.9546 +vn 0.2978 0.0000 0.9546 +vn 0.0000 0.0000 -1.0000 +vn 0.0000 0.0000 1.0000 +usemtl center +s off +f 5/1/1 3/2/1 1/3/1 +f 8/4/2 11/5/2 7/6/2 +f 7/7/3 6/8/3 8/9/3 +f 2/10/4 8/11/4 6/12/4 +f 1/13/5 4/14/5 2/15/5 +f 4/16/6 12/17/6 8/18/6 +f 7/19/7 9/20/7 3/21/7 +f 3/22/8 10/23/8 4/24/8 +f 6/25/9 1/26/9 2/27/9 +f 10/28/10 11/29/10 12/30/10 +f 5/1/1 7/31/1 3/2/1 +f 8/4/2 12/32/2 11/5/2 +f 7/7/3 5/33/3 6/8/3 +f 2/10/4 4/34/4 8/11/4 +f 1/13/5 3/35/5 4/14/5 +f 4/16/6 10/36/6 12/17/6 +f 7/19/7 11/37/7 9/20/7 +f 3/22/8 9/38/8 10/23/8 +f 6/25/9 5/39/9 1/26/9 +f 10/28/10 9/40/10 11/29/10 +usemtl TextArea +f 15/41/10 13/42/10 16/43/10 +f 15/41/10 14/44/10 13/42/10 diff --git a/resources/resources/ewol/theme/shape/Entry.vert b/resources/resources/ewol/theme/shape/Entry.vert deleted file mode 100644 index d02de34..0000000 --- a/resources/resources/ewol/theme/shape/Entry.vert +++ /dev/null @@ -1,50 +0,0 @@ -#ifdef GL_ES -precision mediump float; -precision mediump int; -#endif - -struct widgetStateProperty { - int stateOld; - int stateNew; - float transition; -}; - -// Input : -attribute vec2 EW_coord2d; -attribute vec2 EW_widgetPropertyPos; -uniform mat4 EW_MatrixTransformation; -uniform widgetStateProperty EW_status; -uniform vec4 EW_foreground; -uniform vec4 EW_foregroundSelected; -uniform vec4 EW_foregroundHover; - -// output : -varying vec2 v_position; // This will be passed into the fragment shader. -varying vec2 v_propPos; -varying vec4 v_colorTansition; - -void main(void) { - - gl_Position = EW_MatrixTransformation * vec4(EW_coord2d, 0.0, 1.0); - // transmit position of the curent element (intermolated ...) - v_position = EW_coord2d; - v_propPos = EW_widgetPropertyPos; - - - vec4 colorOld = EW_foreground; - if(EW_status.stateOld==1) { - colorOld = EW_foregroundSelected; - } else if(EW_status.stateOld==2) { - colorOld = EW_foregroundHover; - } - vec4 colorNew = EW_foreground; - if(EW_status.stateNew==1) { - colorNew = EW_foregroundSelected; - } else if(EW_status.stateNew==2) { - colorNew = EW_foregroundHover; - } - - // note : int() is needed for the OpenGL ES platform - v_colorTansition = colorOld*(1.0-EW_status.transition) - + colorNew*EW_status.transition; -} diff --git a/resources/resources/ewol/theme/shape/GuiPaletteColor.png b/resources/resources/ewol/theme/shape/GuiPaletteColor.png new file mode 100644 index 0000000..4d37379 Binary files /dev/null and b/resources/resources/ewol/theme/shape/GuiPaletteColor.png differ diff --git a/resources/resources/ewol/theme/shape/aaRenderShape.frag b/resources/resources/ewol/theme/shape/aaRenderShape.frag new file mode 100644 index 0000000..13d2aa8 --- /dev/null +++ b/resources/resources/ewol/theme/shape/aaRenderShape.frag @@ -0,0 +1,17 @@ +#version 400 core + +#ifdef GL_ES +precision mediump float; +precision mediump int; +#endif + +in vec2 io_textureCoords; + +uniform sampler2D in_textureBase; + +// output: +out vec4 out_Color; + +void main(void) { + out_Color = texture(in_textureBase, io_textureCoords); +} diff --git a/resources/resources/ewol/theme/shape/aaRenderShape.vert b/resources/resources/ewol/theme/shape/aaRenderShape.vert new file mode 100644 index 0000000..e7b436b --- /dev/null +++ b/resources/resources/ewol/theme/shape/aaRenderShape.vert @@ -0,0 +1,22 @@ +#version 400 core + +#ifdef GL_ES +precision mediump float; +precision mediump int; +#endif + +// Input: +layout (location = 0) in vec3 in_position; +layout (location = 1) in vec2 in_textureCoords; + +uniform mat4 in_matrixTransformation; +uniform mat4 in_matrixProjection; +uniform mat4 in_matrixView; + +// output: +out vec2 io_textureCoords; + +void main(void) { + gl_Position = in_matrixProjection * in_matrixView * in_matrixTransformation * vec4(in_position, 1.0); + io_textureCoords = in_textureCoords; +} diff --git a/resources/resources/ewol/theme/shape/empty_area.png b/resources/resources/ewol/theme/shape/empty_area.png new file mode 100644 index 0000000..80bb9cc Binary files /dev/null and b/resources/resources/ewol/theme/shape/empty_area.png differ diff --git a/resources/resources/ewol/theme/shape/pot.blend b/resources/resources/ewol/theme/shape/pot.blend new file mode 100644 index 0000000..95aeb3a Binary files /dev/null and b/resources/resources/ewol/theme/shape/pot.blend differ diff --git a/resources/resources/ewol/theme/shape/pot.blend1 b/resources/resources/ewol/theme/shape/pot.blend1 new file mode 100644 index 0000000..9631f6c Binary files /dev/null and b/resources/resources/ewol/theme/shape/pot.blend1 differ diff --git a/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Appl.java b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Appl.java new file mode 100644 index 0000000..21be3a3 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Appl.java @@ -0,0 +1,80 @@ +package sample.atriasoft.ewol.ComplexWindiows1; + +import org.atriasoft.etk.Configs; +import org.atriasoft.etk.math.Vector2f; +import org.atriasoft.ewol.context.EwolApplication; +import org.atriasoft.ewol.context.EwolContext; + +public class Appl implements EwolApplication { + + //! [ewol_sample_HW_main_application] + private void localCreate(final EwolContext context) { + //! [ewol_sample_HW_main_parse_arguments] + // parse all the argument of the application + for (int iii = 0; iii < context.getCmd().size(); iii++) { + String tmpppp = context.getCmd().get(iii); + if (tmpppp == "-h" || tmpppp == "--help") { + Log.print(" -h/--help display this help"); + System.exit(0); + } + } + //! [ewol_sample_HW_main_parse_arguments] + //! [ewol_sample_HW_main_set_windows_size] + // TODO : Remove this: Move if in the windows properties + context.setSize(new Vector2f(800, 600)); + //! [ewol_sample_HW_main_set_windows_size] + //! [ewol_sample_HW_main_set_font_property] + // select font preference of der with a basic application size + Configs.getConfigFonts().set("FreeSherif", 12); + //! [ewol_sample_HW_main_set_font_property] + //! [ewol_sample_HW_main_set_windows] + // Create the windows + MainWindows basicWindows = new MainWindows(); + // configure the ewol context to use the new windows + context.setWindows(basicWindows); + //! [ewol_sample_HW_main_set_windows] + } + + @Override + public void onCreate(final EwolContext context) { + Log.info("Application onCreate: [BEGIN]"); + localCreate(context); + Log.info("Application onCreate: [ END ]"); + } + + @Override + public void onDestroy(final EwolContext context) { + Log.info("Application onDestroy: [BEGIN]"); + + Log.info("Application onDestroy: [ END ]"); + } + + @Override + public void onPause(final EwolContext context) { + Log.info("Application onPause: [BEGIN]"); + + Log.info("Application onPause: [ END ]"); + } + + @Override + public void onResume(final EwolContext context) { + Log.info("Application onResume: [BEGIN]"); + + Log.info("Application onResume: [ END ]"); + } + + @Override + public void onStart(final EwolContext context) { + Log.info("Application onStart: [BEGIN]"); + + Log.info("Application onStart: [ END ]"); + } + + @Override + public void onStop(final EwolContext context) { + Log.info("Application onStop: [BEGIN]"); + + Log.info("Application onStop: [ END ]"); + } + +} \ No newline at end of file diff --git a/samples/src/sample/atriasoft/ewol/ComplexWindiows1/ComplexeWindows1Main.java b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/ComplexeWindows1Main.java new file mode 100644 index 0000000..e1367cd --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/ComplexeWindows1Main.java @@ -0,0 +1,15 @@ +package sample.atriasoft.ewol.ComplexWindiows1; + +import org.atriasoft.etk.Uri; +import org.atriasoft.ewol.Ewol; + +public class ComplexeWindows1Main { + public static void main(final String[] args) { + Ewol.init(); + //Uri.addLibrary("ne", MainCollisionTest.class, "testDataLoxelEngine/"); + Uri.setApplication(ComplexeWindows1Main.class); + Ewol.run(new Appl(), args); + } + + private ComplexeWindows1Main() {} +} diff --git a/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Log.java b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Log.java new file mode 100644 index 0000000..a0581e6 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/Log.java @@ -0,0 +1,39 @@ +package sample.atriasoft.ewol.ComplexWindiows1; + +public class Log { + private static final String LIBNAME = "LoxelEngine"; + + public static void critical(final String data) { + System.out.println("[C] " + Log.LIBNAME + " | " + data); + } + + public static void debug(final String data) { + System.out.println("[D] " + Log.LIBNAME + " | " + data); + } + + public static void error(final String data) { + System.out.println("[E] " + Log.LIBNAME + " | " + data); + } + + public static void info(final String data) { + System.out.println("[I] " + Log.LIBNAME + " | " + data); + } + + public static void print(final String data) { + System.out.println(data); + } + + public static void todo(final String data) { + System.out.println("[TODO] " + Log.LIBNAME + " | " + data); + } + + public static void verbose(final String data) { + System.out.println("[V] " + Log.LIBNAME + " | " + data); + } + + public static void warning(final String data) { + System.out.println("[W] " + Log.LIBNAME + " | " + data); + } + + private Log() {} +} diff --git a/samples/src/sample/atriasoft/ewol/ComplexWindiows1/MainWindows.java b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/MainWindows.java new file mode 100644 index 0000000..8a50c98 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/ComplexWindiows1/MainWindows.java @@ -0,0 +1,71 @@ +package sample.atriasoft.ewol.ComplexWindiows1; + +import org.atriasoft.etk.Color; +import org.atriasoft.etk.Dimension; +import org.atriasoft.etk.Distance; +import org.atriasoft.etk.math.Vector2b; +import org.atriasoft.etk.math.Vector2f; +import org.atriasoft.ewol.widget.Sizer; +import org.atriasoft.ewol.widget.Sizer.DisplayMode; +import org.atriasoft.ewol.widget.Spacer; +import org.atriasoft.ewol.widget.Windows; + +public class MainWindows extends Windows { + + public MainWindows() { + //! [ewol_sample_HW_windows_title] + setPropertyTitle("Simple sample test"); + //EwolObject.getContext().getFontDefault().setName("FreeSans"); + Sizer sizerMain = new Sizer(DisplayMode.modeVert); + sizerMain.setPropertyExpand(new Vector2b(true, true)); + sizerMain.setPropertyFill(new Vector2b(true, true)); + setSubWidget(sizerMain); + + Sizer sizerHori1 = new Sizer(DisplayMode.modeHori); + sizerHori1.setPropertyExpand(new Vector2b(true, true)); + sizerHori1.setPropertyFill(new Vector2b(true, true)); + sizerMain.subWidgetAdd(sizerHori1); + + Sizer sizerHori2 = new Sizer(DisplayMode.modeHori); + sizerHori2.setPropertyExpand(new Vector2b(true, true)); + sizerHori2.setPropertyFill(new Vector2b(true, true)); + sizerMain.subWidgetAdd(sizerHori2); + + { + Spacer simpleSpacer = new Spacer(); + simpleSpacer.setPropertyMinSize(new Dimension(new Vector2f(100, 100), Distance.PIXEL)); + simpleSpacer.setPropertyColor(Color.ALICE_BLUE); + simpleSpacer.setPropertyExpand(new Vector2b(true, true)); + simpleSpacer.setPropertyFill(new Vector2b(true, true)); + sizerHori1.subWidgetAdd(simpleSpacer); + } + { + Spacer simpleSpacer = new Spacer(); + simpleSpacer.setPropertyColor(Color.DARK_GREEN); + simpleSpacer.setPropertyExpand(new Vector2b(true, true)); + simpleSpacer.setPropertyFill(new Vector2b(true, true)); + sizerHori1.subWidgetAdd(simpleSpacer); + } + { + Spacer simpleSpacer = new Spacer(); + simpleSpacer.setPropertyColor(Color.CHOCOLATE); + simpleSpacer.setPropertyExpand(new Vector2b(true, true)); + simpleSpacer.setPropertyFill(new Vector2b(true, true)); + sizerHori1.subWidgetAdd(simpleSpacer); + } + { + Spacer simpleSpacer = new Spacer(); + simpleSpacer.setPropertyColor(Color.GREEN_YELLOW); + simpleSpacer.setPropertyExpand(new Vector2b(true, true)); + simpleSpacer.setPropertyFill(new Vector2b(true, true)); + sizerHori2.subWidgetAdd(simpleSpacer); + } + { + Spacer simpleSpacer = new Spacer(); + simpleSpacer.setPropertyColor(Color.PINK); + simpleSpacer.setPropertyExpand(new Vector2b(true, true)); + simpleSpacer.setPropertyFill(new Vector2b(true, true)); + sizerHori2.subWidgetAdd(simpleSpacer); + } + } +} diff --git a/samples/src/sample/atriasoft/ewol/sampleEntry/Appl.java b/samples/src/sample/atriasoft/ewol/sampleEntry/Appl.java new file mode 100644 index 0000000..8c77041 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/sampleEntry/Appl.java @@ -0,0 +1,80 @@ +package sample.atriasoft.ewol.sampleEntry; + +import org.atriasoft.etk.Configs; +import org.atriasoft.etk.math.Vector2f; +import org.atriasoft.ewol.context.EwolApplication; +import org.atriasoft.ewol.context.EwolContext; + +public class Appl implements EwolApplication { + + //! [ewol_sample_HW_main_application] + private void localCreate(final EwolContext context) { + //! [ewol_sample_HW_main_parse_arguments] + // parse all the argument of the application + for (int iii = 0; iii < context.getCmd().size(); iii++) { + String tmpppp = context.getCmd().get(iii); + if (tmpppp == "-h" || tmpppp == "--help") { + Log.print(" -h/--help display this help"); + System.exit(0); + } + } + //! [ewol_sample_HW_main_parse_arguments] + //! [ewol_sample_HW_main_set_windows_size] + // TODO : Remove this: Move if in the windows properties + context.setSize(new Vector2f(800, 600)); + //! [ewol_sample_HW_main_set_windows_size] + //! [ewol_sample_HW_main_set_font_property] + // select font preference of der with a basic application size + Configs.getConfigFonts().set("FreeSherif", 48); + //! [ewol_sample_HW_main_set_font_property] + //! [ewol_sample_HW_main_set_windows] + // Create the windows + MainWindows basicWindows = new MainWindows(); + // configure the ewol context to use the new windows + context.setWindows(basicWindows); + //! [ewol_sample_HW_main_set_windows] + } + + @Override + public void onCreate(final EwolContext context) { + Log.info("Application onCreate: [BEGIN]"); + localCreate(context); + Log.info("Application onCreate: [ END ]"); + } + + @Override + public void onDestroy(final EwolContext context) { + Log.info("Application onDestroy: [BEGIN]"); + + Log.info("Application onDestroy: [ END ]"); + } + + @Override + public void onPause(final EwolContext context) { + Log.info("Application onPause: [BEGIN]"); + + Log.info("Application onPause: [ END ]"); + } + + @Override + public void onResume(final EwolContext context) { + Log.info("Application onResume: [BEGIN]"); + + Log.info("Application onResume: [ END ]"); + } + + @Override + public void onStart(final EwolContext context) { + Log.info("Application onStart: [BEGIN]"); + + Log.info("Application onStart: [ END ]"); + } + + @Override + public void onStop(final EwolContext context) { + Log.info("Application onStop: [BEGIN]"); + + Log.info("Application onStop: [ END ]"); + } + +} \ No newline at end of file diff --git a/samples/src/sample/atriasoft/ewol/sampleEntry/Log.java b/samples/src/sample/atriasoft/ewol/sampleEntry/Log.java new file mode 100644 index 0000000..ea6a16d --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/sampleEntry/Log.java @@ -0,0 +1,39 @@ +package sample.atriasoft.ewol.sampleEntry; + +public class Log { + private static final String LIBNAME = "sampleEntry"; + + public static void critical(final String data) { + System.out.println("[C] " + Log.LIBNAME + " | " + data); + } + + public static void debug(final String data) { + System.out.println("[D] " + Log.LIBNAME + " | " + data); + } + + public static void error(final String data) { + System.out.println("[E] " + Log.LIBNAME + " | " + data); + } + + public static void info(final String data) { + System.out.println("[I] " + Log.LIBNAME + " | " + data); + } + + public static void print(final String data) { + System.out.println(data); + } + + public static void todo(final String data) { + System.out.println("[TODO] " + Log.LIBNAME + " | " + data); + } + + public static void verbose(final String data) { + System.out.println("[V] " + Log.LIBNAME + " | " + data); + } + + public static void warning(final String data) { + System.out.println("[W] " + Log.LIBNAME + " | " + data); + } + + private Log() {} +} diff --git a/samples/src/sample/atriasoft/ewol/sampleEntry/MainWindows.java b/samples/src/sample/atriasoft/ewol/sampleEntry/MainWindows.java new file mode 100644 index 0000000..c33f8c4 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/sampleEntry/MainWindows.java @@ -0,0 +1,17 @@ +package sample.atriasoft.ewol.sampleEntry; + +import org.atriasoft.etk.math.Vector2b; +import org.atriasoft.ewol.widget.Entry; +import org.atriasoft.ewol.widget.Windows; + +public class MainWindows extends Windows { + + public MainWindows() { + setPropertyTitle("Simple sample test"); + //EwolObject.getContext().getFontDefault().setName("FreeSans"); + Entry simpleEntry = new Entry(); + simpleEntry.setPropertyExpand(new Vector2b(true, true)); + simpleEntry.setPropertyFill(new Vector2b(true, false)); + setSubWidget(simpleEntry); + } +} diff --git a/samples/src/sample/atriasoft/ewol/sampleEntry/SampleEntryMain.java b/samples/src/sample/atriasoft/ewol/sampleEntry/SampleEntryMain.java new file mode 100644 index 0000000..4784170 --- /dev/null +++ b/samples/src/sample/atriasoft/ewol/sampleEntry/SampleEntryMain.java @@ -0,0 +1,15 @@ +package sample.atriasoft.ewol.sampleEntry; + +import org.atriasoft.etk.Uri; +import org.atriasoft.ewol.Ewol; + +public class SampleEntryMain { + public static void main(final String[] args) { + Ewol.init(); + //Uri.addLibrary("ne", MainCollisionTest.class, "testDataLoxelEngine/"); + Uri.setApplication(MainWindows.class); + Ewol.run(new Appl(), args); + } + + private SampleEntryMain() {} +} diff --git a/samples/src/sample/atriasoft/ewol/simpleWindowsWithImage/Appl.java b/samples/src/sample/atriasoft/ewol/simpleWindowsWithImage/Appl.java index 4631833..94895eb 100644 --- a/samples/src/sample/atriasoft/ewol/simpleWindowsWithImage/Appl.java +++ b/samples/src/sample/atriasoft/ewol/simpleWindowsWithImage/Appl.java @@ -1,5 +1,6 @@ package sample.atriasoft.ewol.simpleWindowsWithImage; +import org.atriasoft.etk.Configs; import org.atriasoft.etk.math.Vector2f; import org.atriasoft.ewol.context.EwolApplication; import org.atriasoft.ewol.context.EwolContext; @@ -24,7 +25,7 @@ public class Appl implements EwolApplication { //! [ewol_sample_HW_main_set_windows_size] //! [ewol_sample_HW_main_set_font_property] // select font preference of der with a basic application size - context.getFontDefault().set("FreeSherif", 12); + Configs.getConfigFonts().set("FreeSherif", 12); //! [ewol_sample_HW_main_set_font_property] //! [ewol_sample_HW_main_set_windows] // Create the windows diff --git a/src/module-info.java b/src/module-info.java index 0f4a25f..c857ebe 100644 --- a/src/module-info.java +++ b/src/module-info.java @@ -26,4 +26,6 @@ open module org.atriasoft.ewol { requires transitive org.atriasoft.exml; requires transitive org.atriasoft.ejson; requires transitive io.scenarium.logger; + requires org.atriasoft.loader3d; + requires org.atriasoft.egami; } diff --git a/src/org/atriasoft/esignal/Connection.java b/src/org/atriasoft/esignal/Connection.java index 2e5f4e3..1282723 100644 --- a/src/org/atriasoft/esignal/Connection.java +++ b/src/org/atriasoft/esignal/Connection.java @@ -2,4 +2,9 @@ package org.atriasoft.esignal; public class Connection { + public void disconnect() { + // TODO Auto-generated method stub + + } + } diff --git a/src/org/atriasoft/esignal/Signal.java b/src/org/atriasoft/esignal/Signal.java index 853ea1e..04af838 100644 --- a/src/org/atriasoft/esignal/Signal.java +++ b/src/org/atriasoft/esignal/Signal.java @@ -7,8 +7,8 @@ import java.util.List; import java.util.function.Consumer; class ConnectedElement { - private final WeakReference reference; private final Consumer consumer; + private final WeakReference reference; public ConnectedElement(final WeakReference reference, final Consumer consumer) { this.reference = reference; diff --git a/src/org/atriasoft/ewol/Padding.java b/src/org/atriasoft/ewol/Padding.java index af38df5..b3f201f 100644 --- a/src/org/atriasoft/ewol/Padding.java +++ b/src/org/atriasoft/ewol/Padding.java @@ -8,30 +8,41 @@ package org.atriasoft.ewol; /** * @breif Simple class to abstarct the padding porperty. */ -public class Padding { - private float xLeft; - private float xRight; - private float yBottom; // !< this represent the 4 padding value Left top right buttom (like css) - private float yTop; +@SuppressWarnings("preview") +public record Padding( + float left, + float top, + float right, + float bottom // !< this represent the 4 padding value Left top right buttom (like css) +) { + + public static final Padding ZERO = new Padding(0, 0, 0, 0); public Padding() { - setValue(); + this(0, 0, 0, 0); } - public Padding(final float xLeft) { - setValue(xLeft); + public Padding(final float left) { + this(left, 0, 0, 0); } - public Padding(final float xLeft, final float yt) { - setValue(xLeft, yt); + public Padding(final float left, final float top) { + this(left, top, 0, 0); } - public Padding(final float xLeft, final float yt, final float xr) { - setValue(xLeft, yt, xr); + public Padding(final float left, final float top, final float right) { + this(left, top, right, 0); } - public Padding(final float xLeft, final float yt, final float xr, final float yb) { - setValue(xLeft, yt, xr, yb); + public Padding(final float left, final float top, final float right, final float bottom) { + this.left = left; + this.top = top; + this.right = right; + this.bottom = bottom; + } + + public Padding(final double left, final double top, final double right, final double bottom) { + this((float) left, (float) top, (float) right, (float) bottom); } /** @@ -39,95 +50,36 @@ public class Padding { * @param v The vector to add to this one */ public Padding add(final Padding v) { - this.xLeft += v.xLeft; - this.yTop += v.yTop; - this.xRight += v.xRight; - this.yBottom += v.yBottom; - return this; + return new Padding(this.left + v.left, this.top + v.top, this.right + v.right, this.bottom + v.bottom); } - // ! @previous - public Padding addNew(final Padding v) { - return new Padding(this.xLeft + v.xLeft, this.yTop + v.yTop, this.xRight + v.xRight, this.yBottom + v.yBottom); + public Padding withLeft(final float left) { + return new Padding(left, this.top, this.right, this.bottom); } - public void setValue() { - this.xLeft = 0; - this.yTop = 0; - this.xRight = 0; - this.yBottom = 0; + public Padding withRight(final float right) { + return new Padding(this.left, this.top, right, this.bottom); } - public void setValue(final float xLeft) { - this.xLeft = xLeft; - this.yTop = 0; - this.xRight = 0; - this.yBottom = 0; + public Padding withButtom(final float bottom) { + return new Padding(this.left, this.top, this.right, bottom); } - public void setValue(final float xLeft, final float yt) { - this.xLeft = xLeft; - this.yTop = yt; - this.xRight = 0; - this.yBottom = 0; - } - - public void setValue(final float xLeft, final float yt, final float xr) { - this.xLeft = xLeft; - this.yTop = yt; - this.xRight = xr; - this.yBottom = 0; - } - - public void setValue(final float xLeft, final float yt, final float xr, final float yb) { - this.xLeft = xLeft; - this.yTop = yt; - this.xRight = xr; - this.yBottom = yb; - } - - public void setXLeft(final float val) { - this.xLeft = val; - } - - public void setXRight(final float val) { - this.xRight = val; - } - - public void setYButtom(final float val) { - this.yBottom = val; - } - - public void setYTop(final float val) { - this.yTop = val; + public Padding withTop(final float top) { + return new Padding(this.left, top, this.right, this.bottom); } @Override public String toString() { - return "{" + xLeft() + "," + yTop() + "," + xRight() + "," + yButtom() + "}"; + return "{" + left() + "," + top() + "," + right() + "," + bottom() + "}"; } public float x() { - return this.xLeft + this.xRight; - } - - public float xLeft() { - return this.xLeft; - } - - public float xRight() { - return this.xRight; + return this.left + this.right; } public float y() { - return this.yTop + this.yBottom; + return this.top + this.bottom; } - public float yButtom() { - return this.yBottom; - } - - public float yTop() { - return this.yTop; - } } diff --git a/src/org/atriasoft/ewol/annotation/EwolSignal.java b/src/org/atriasoft/ewol/annotation/EwolSignal.java index 292b528..88fea5d 100644 --- a/src/org/atriasoft/ewol/annotation/EwolSignal.java +++ b/src/org/atriasoft/ewol/annotation/EwolSignal.java @@ -1,6 +1,7 @@ package org.atriasoft.ewol.annotation; public @interface EwolSignal { - String[] name(); + String description() default ""; + String[] name(); } diff --git a/src/org/atriasoft/ewol/compositing/CompositingDrawing.java b/src/org/atriasoft/ewol/compositing/CompositingDrawing.java index 3af63fa..392dc66 100644 --- a/src/org/atriasoft/ewol/compositing/CompositingDrawing.java +++ b/src/org/atriasoft/ewol/compositing/CompositingDrawing.java @@ -28,8 +28,11 @@ public class CompositingDrawing extends Compositing { private Vector3f clippingPosStop = new Vector3f(0, 0, 0); // !< Clipping stop position private Color color = Color.BLACK; // !< The text foreground color private Color colorBg = Color.NONE; // !< The text background color - private int oGLMatrix = -1; // !< openGL id on the element (transformation matrix) - private int oGLMatrixPosition = -1; // !< position matrix + //private int oGLMatrix = -1; // !< openGL id on the element (transformation matrix) + //private int oGLMatrixPosition = -1; // !< position matrix + private int oGLMatrixProjection = -1; //!< openGL id on the element (Projection matrix) + private int oGLMatrixTransformation = -1; //!< openGL id on the element (transformation matrix) + private int oGLMatrixView = -1; //!< openGL id on the element (view matrix) private ResourceProgram oGLprogram; // !< pointer on the opengl display program private final List outColors = new ArrayList<>(); private final List outTriangles = new ArrayList<>(); @@ -185,11 +188,13 @@ public class CompositingDrawing extends Compositing { return; } // set Matrix : translation/positionMatrix - final Matrix4f tmpMatrix = OpenGL.getMatrix().multiply(this.matrixApply); + Matrix4f projMatrix = OpenGL.getMatrix(); + Matrix4f camMatrix = OpenGL.getCameraMatrix(); this.oGLprogram.use(); this.vbo.bindForRendering(); - this.oGLprogram.uniformMatrix(this.oGLMatrix, tmpMatrix); - this.oGLprogram.uniformMatrix(this.oGLMatrixPosition, Matrix4f.IDENTITY); + this.oGLprogram.uniformMatrix(this.oGLMatrixProjection, projMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixTransformation, this.matrixApply); + this.oGLprogram.uniformMatrix(this.oGLMatrixView, camMatrix); // Request the draw of the elements: this.vbo.renderArrays(OpenGL.RenderMode.triangle); this.vbo.unBindForRendering(); @@ -257,18 +262,34 @@ public class CompositingDrawing extends Compositing { } } - public void lineRel(final Vector2f vect) { - lineRel(new Vector3f(vect.x(), vect.y(), 0)); - } - /** * Relative drawing a line (spacial vector) * @param vect Vector of the curent line. */ + public void lineRel(final float xxx, final float yyy) { + lineTo(this.position.add(new Vector3f(xxx, yyy, 0))); + } + + public void lineRel(final float xxx, final float yyy, final float zzz) { + lineTo(this.position.add(new Vector3f(xxx, yyy, zzz))); + } + + public void lineRel(final Vector2f vect) { + lineRel(new Vector3f(vect.x(), vect.y(), 0)); + } + public void lineRel(final Vector3f vect) { lineTo(this.position.add(vect)); } + public void lineTo(final float xxx, final float yyy) { + lineTo(new Vector3f(xxx, yyy, 0)); + } + + public void lineTo(final float xxx, final float yyy, final float zzz) { + lineTo(new Vector3f(xxx, yyy, zzz)); + } + public void lineTo(final Vector2f dest) { lineTo(new Vector3f(dest.x(), dest.y(), 0)); } @@ -323,11 +344,20 @@ public class CompositingDrawing extends Compositing { if (this.oGLprogram != null) { //this.oGLPosition = this.oGLprogram.getAttribute("in_coord3d"); //this.oGLColor = this.oGLprogram.getAttribute("in_color"); - this.oGLMatrix = this.oGLprogram.getUniform("in_MatrixTransformation"); - this.oGLMatrixPosition = this.oGLprogram.getUniform("in_MatrixPosition"); + this.oGLMatrixTransformation = this.oGLprogram.getUniform("in_matrixTransformation"); + this.oGLMatrixProjection = this.oGLprogram.getUniform("in_matrixProjection"); + this.oGLMatrixView = this.oGLprogram.getUniform("in_matrixView"); } } + public void rectangle(final float xxx, final float yyy) { + rectangle(new Vector3f(xxx, yyy, 0)); + } + + public void rectangle(final float xxx, final float yyy, final float zzz) { + rectangle(new Vector3f(xxx, yyy, zzz)); + } + public void rectangle(final Vector2f dest) { rectangle(new Vector3f(dest.x(), dest.y(), 0)); } @@ -384,6 +414,14 @@ public class CompositingDrawing extends Compositing { setPoint(new Vector3f(dxA, dyD, 0)); } + public void rectangleWidth(final float xxx, final float yyy) { + rectangleWidth(new Vector3f(xxx, yyy, 0)); + } + + public void rectangleWidth(final float xxx, final float yyy, final float zzz) { + rectangleWidth(new Vector3f(xxx, yyy, zzz)); + } + public void rectangleWidth(final Vector2f size) { rectangleWidth(new Vector3f(size.x(), size.y(), 0)); } @@ -472,26 +510,42 @@ public class CompositingDrawing extends Compositing { this.vbo.flush(); } + public void setPos(final float xxx, final float yyy) { + setPos(new Vector3f(xxx, yyy, 0)); + } + + public void setPos(final float xxx, final float yyy, final float zzz) { + setPos(new Vector3f(xxx, yyy, zzz)); + } + public void setPos(final Vector2f pos) { setPos(new Vector3f(pos.x(), pos.y(), 0)); } /** - * set position for the next text writen + * set position for the next text written * @param pos Position of the text (in 3D) */ public void setPos(final Vector3f pos) { this.position = pos; } - public void setRelPos(final Vector2f pos) { - setRelPos(new Vector3f(pos.x(), pos.y(), 0)); + public void setRelPos(final float xxx, final float yyy) { + this.position = this.position.add(xxx, yyy, 0); } /** * set relative position for the next text writen * @param pos ofset apply of the text (in 3D) */ + public void setRelPos(final float xxx, final float yyy, final float zzz) { + this.position = this.position.add(xxx, yyy, zzz); + } + + public void setRelPos(final Vector2f pos) { + setRelPos(new Vector3f(pos.x(), pos.y(), 0)); + } + public void setRelPos(final Vector3f pos) { this.position = this.position.add(pos); } diff --git a/src/org/atriasoft/ewol/compositing/CompositingImage.java b/src/org/atriasoft/ewol/compositing/CompositingImage.java index ecabbe5..8cc60c9 100644 --- a/src/org/atriasoft/ewol/compositing/CompositingImage.java +++ b/src/org/atriasoft/ewol/compositing/CompositingImage.java @@ -5,7 +5,7 @@ */ package org.atriasoft.ewol.compositing; -import org.atriasoft.egami.Image; +import org.atriasoft.egami.ImageByteRGBA; import org.atriasoft.etk.Color; import org.atriasoft.etk.Uri; import org.atriasoft.etk.math.FMath; @@ -403,7 +403,7 @@ public class CompositingImage extends Compositing { this.position = this.position.add(pos); } - public void setSource(final Image image) { + public void setSource(final ImageByteRGBA image) { clear(); this.filename = null; this.requestSize = image.getSize(); diff --git a/src/org/atriasoft/ewol/compositing/CompositingText.java b/src/org/atriasoft/ewol/compositing/CompositingText.java index d239668..83907bb 100644 --- a/src/org/atriasoft/ewol/compositing/CompositingText.java +++ b/src/org/atriasoft/ewol/compositing/CompositingText.java @@ -10,11 +10,11 @@ import java.util.ArrayList; import java.util.List; import org.atriasoft.etk.Color; +import org.atriasoft.etk.Configs; import org.atriasoft.etk.Uri; import org.atriasoft.etk.math.Matrix4f; import org.atriasoft.etk.math.Vector2f; import org.atriasoft.etk.math.Vector3f; -import org.atriasoft.ewol.Ewol; import org.atriasoft.ewol.internal.Log; import org.atriasoft.ewol.resource.ResourceTexturedFont; import org.atriasoft.ewol.resource.font.FontMode; @@ -100,10 +100,13 @@ public class CompositingText extends TextBase { return; } // set Matrix : translation/positionMatrix - final Matrix4f tmpMatrix = OpenGL.getMatrix().multiply(this.matrixApply); + final Matrix4f projMatrix = OpenGL.getMatrix(); + final Matrix4f camMatrix = OpenGL.getCameraMatrix(); this.oGLprogram.use(); this.vbo.bindForRendering(); - this.oGLprogram.uniformMatrix(this.oGLMatrix, tmpMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixProjection, projMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixTransformation, this.matrixApply); + this.oGLprogram.uniformMatrix(this.oGLMatrixView, camMatrix); // Texture : this.oGLprogram.setTexture0(this.oGLtexID, this.font.getRendererId()); this.oGLprogram.uniformInt(this.oGLtextWidth, this.font.getOpenGlSize().x()); @@ -136,10 +139,11 @@ public class CompositingText extends TextBase { // set Matrix : translation/positionMatrix final Matrix4f projMatrix = OpenGL.getMatrix(); final Matrix4f camMatrix = OpenGL.getCameraMatrix(); - final Matrix4f tmpMatrix = projMatrix.multiply(camMatrix).multiply(transformationMatrix); this.oGLprogram.use(); this.vbo.bindForRendering(); - this.oGLprogram.uniformMatrix(this.oGLMatrix, tmpMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixProjection, projMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixTransformation, transformationMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixView, camMatrix); // Texture: this.oGLprogram.setTexture0(this.oGLtexID, this.font.getRendererId()); this.oGLprogram.uniformInt(this.oGLtextWidth, this.font.getOpenGlSize().x()); @@ -219,9 +223,9 @@ public class CompositingText extends TextBase { /* * Bitmap position xA xB yC *------* | | | | yD *------* */ - float dxA = this.position.x() /*+ myGlyphProperty.bearing.x()*/ + kerningOffset; + float dxA = this.position.x() + myGlyphProperty.getTextureRenderOffset().x() + kerningOffset; float dxB = dxA + myGlyphProperty.sizeTexture.x(); - float dyC = this.position.y() /*+ myGlyphProperty.bearing.y()*/ + fontHeigh - fontSize; + float dyC = this.position.y() + myGlyphProperty.getTextureRenderOffset().y() + fontHeigh - fontSize; float dyD = dyC - myGlyphProperty.sizeTexture.y(); float tuA = myGlyphProperty.texturePosStart.x(); @@ -346,12 +350,12 @@ public class CompositingText extends TextBase { // remove old one final ResourceTexturedFont previousFont = this.font; if (fontSize <= 0) { - fontSize = Ewol.getContext().getFontDefault().getSize(); + fontSize = Configs.getConfigFonts().getSize(); } if (fontName.isEmpty()) { - fontName = Ewol.getContext().getFontDefault().getName(); + fontName = Configs.getConfigFonts().getName(); } - Uri fontUri = Ewol.getContext().getFontDefault().getFontUri(fontName).clone(); + Uri fontUri = Configs.getConfigFonts().getFontUri(fontName).clone(); fontUri.setproperty("size", Integer.toString(fontSize)); Log.verbose("plop : " + fontName + " size=" + fontSize + " result :" + fontName); // link to new one diff --git a/src/org/atriasoft/ewol/compositing/GuiShape.java b/src/org/atriasoft/ewol/compositing/GuiShape.java new file mode 100644 index 0000000..c7d1d9f --- /dev/null +++ b/src/org/atriasoft/ewol/compositing/GuiShape.java @@ -0,0 +1,440 @@ +package org.atriasoft.ewol.compositing; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +import org.atriasoft.etk.Uri; +import org.atriasoft.etk.math.Matrix4f; +import org.atriasoft.etk.math.Vector2f; +import org.atriasoft.etk.math.Vector2i; +import org.atriasoft.etk.math.Vector3f; +import org.atriasoft.ewol.Padding; +import org.atriasoft.ewol.event.EventTime; +import org.atriasoft.ewol.internal.Log; +import org.atriasoft.ewol.resource.ResourceConfigFile; +import org.atriasoft.ewol.resource.ResourceTextureFile; +import org.atriasoft.ewol.resource.TextureFilter; +import org.atriasoft.gale.backend3d.OpenGL; +import org.atriasoft.gale.backend3d.OpenGL.Flag; +import org.atriasoft.gale.resource.ResourceProgram; +import org.atriasoft.loader3d.resources.ResourceStaticMeshObjBynamic; + +/** + * @brief the Shaper system is a basic theme configuration for every widget, it corresponds at a background display described by a pool of files + */ +// TODO : load image +// TODO : Abstaraction between states (call by name and the system greate IDs +public class GuiShape extends Compositing { + private static final int SHAPER_POS_BOTTOM = 3; + private static final int SHAPER_POS_LEFT = 0; + private static final int SHAPER_POS_RIGHT = 2; + private static final int SHAPER_POS_TOP = 1; + private int confIdChangeTime = -1; //!< ConfigFile padding transition time property + private int confIdImagePaletteFile = -1; //!< Palette of the display + private int confIdImagePaletteMode = -1; //!< Mode to load the image file ... 'nearest', 'linear' + private final int[] confIdPaddingIn = new int[4]; //!< Padding in property : X-left X-right Y-top Y-buttom + private final int[] confIdPaddingOut = new int[4]; //!< Padding out property : X-left X-right Y-top Y-buttom + // External theme config: + private ResourceConfigFile config = null; //!< pointer on the config file resources + + private int confObjectFile = -1; //!< Config Id of the object file to display + private int confProgramFileFrag = -1; //!< ConfigFile opengGl program Name + private int confProgramFileVert = -1; //!< ConfigFile opengGl program Name + private final List listAssiciatedId = new ArrayList<>(); //!< Correlation ID between ColorProperty (Y) and OpenGL Program (X) + // internal needed data : + private int nextStatusRequested = -1; //!< when status is changing, this represent the next step of it + private int oGLMatrixProjection = -1; //!< openGL id on the element (Projection matrix) + private int oGLMatrixTransformation = -1; //!< openGL id on the element (transformation matrix) + private int oGLMatrixView = -1; //!< openGL id on the element (view matrix) + // openGL shaders programs: + private ResourceProgram oGLprogram = null; //!< pointer on the opengl display program + private int oGLtexID = -1; //!< openGL id on the element (texture image) + // For the Image : + private ResourceTextureFile resourceTexture = null; //!< texture resources (for the image) + private ResourceStaticMeshObjBynamic shape = null; + private Padding sizeObject = Padding.ZERO; + private int stateActivate = -1; //!< Activate state of the element + private final int stateNew = -1; //!< destination state + private final int stateOld = -1; //!< previous state + private final float stateTransition = 0; //!< working state between 2 states + private Matrix4f transform = Matrix4f.IDENTITY; + private Uri uri; //!< Name of the configuration of the shaper. + private float[] verticesToModify = {}; + + /** + * @brief generic constructor + * @param _uri URI of the file that might be loaded + */ + public GuiShape(final Uri uri) { + this.uri = uri; + for (int iii = 0; iii < 4; ++iii) { + this.confIdPaddingOut[iii] = -1; + this.confIdPaddingIn[iii] = -1; + } + loadProgram(); + } + + /** + * @brief change the current status in an other + * @param _newStatusId the next new status requested + * @return true The widget must call this fuction periodicly (and redraw itself) + * @return false No need to request the periodic call. + */ + public boolean changeStatusIn(final int newStatusId) { + if (newStatusId != this.stateNew) { + this.nextStatusRequested = newStatusId; + return true; + } + if (this.nextStatusRequested != -1 || this.stateNew != this.stateOld) { + return true; + } + return false; + } + + /** + * @brief clear alll tre registered element in the current element + */ + @Override + public void clear() {} + + /** + * @brief draw All the refistered text in the current element on openGL + */ + @Override + public void draw(final boolean disableDepthTest) { + if (this.config == null) { + // this is a normal case ... the user can choice to have no config basic file ... + return; + } + if (this.oGLprogram == null) { + Log.error("No shader ..."); + } + OpenGL.enable(Flag.flag_depthTest); + // set Matrix : translation/positionMatrix + Matrix4f projMatrix = OpenGL.getMatrix(); + Matrix4f camMatrix = OpenGL.getCameraMatrix(); + Matrix4f tmpMatrix = this.matrixApply.multiply(this.transform); + this.oGLprogram.use(); + this.shape.bindForRendering(); + this.oGLprogram.uniformMatrix(this.oGLMatrixProjection, projMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixTransformation, tmpMatrix); + this.oGLprogram.uniformMatrix(this.oGLMatrixView, camMatrix); + // Texture: + this.oGLprogram.setTexture0(this.oGLtexID, this.resourceTexture.getRendererId()); + // Request the draw of the elements: + this.shape.render(); + + this.shape.unBindForRendering(); + this.oGLprogram.unUse(); + OpenGL.disable(Flag.flag_depthTest); + } + + @Override + public void flush() { + // TODO Auto-generated method stub + + } + + /** + * @brief get the padding declared by the user in the config file + * @return the padding property + */ + public Padding getBorder() { + return this.sizeObject; + } + + /** + * @brief get the current displayed status of the shaper + * @return The Status Id + */ + public int getCurrentDisplayedStatus() { + return this.stateNew; + } + + /** + * @brief get the next displayed status of the shaper + * @return The next status Id (-1 if no status in next) + */ + public int getNextDisplayedStatus() { + return this.nextStatusRequested; + } + + /** + * @brief get the padding declared by the user in the config file + * @return the padding property + */ + public Padding getPadding() { + return getPaddingOut().add(getBorder()).add(getPaddingIn()); + } + + public Padding getPaddingIn() { + Padding out = Padding.ZERO; + if (this.config != null) { + out = new Padding(this.config.getNumber(this.confIdPaddingIn[GuiShape.SHAPER_POS_LEFT]), this.config.getNumber(this.confIdPaddingIn[GuiShape.SHAPER_POS_TOP]), + this.config.getNumber(this.confIdPaddingIn[GuiShape.SHAPER_POS_RIGHT]), this.config.getNumber(this.confIdPaddingIn[GuiShape.SHAPER_POS_BOTTOM])); + } + return out; + } + + public Padding getPaddingOut() { + Padding out = Padding.ZERO; + if (this.config != null) { + out = new Padding(this.config.getNumber(this.confIdPaddingOut[GuiShape.SHAPER_POS_LEFT]), this.config.getNumber(this.confIdPaddingOut[GuiShape.SHAPER_POS_TOP]), + this.config.getNumber(this.confIdPaddingOut[GuiShape.SHAPER_POS_RIGHT]), this.config.getNumber(this.confIdPaddingOut[GuiShape.SHAPER_POS_BOTTOM])); + } + return out; + } + + /** + * @brief get the shaper file Source + * @return the shapper file name + */ + public Uri getSource() { + return this.uri; + } + + /** + * @brief get the current trasion status + * @return value of the transition status (0.0f when no activity) + */ + public float getTransitionStatus() { + return this.stateTransition; + } + + /** + * @brief Sometimes the user declare an image but not allocate the ressources all the time, this is to know it .. + * @return the validity od the resources. + */ + public boolean hasSources() { + return this.oGLprogram != null; + } + + /** + * @brief load the openGL program and get all the ID needed + */ + private void loadProgram() { + if (this.uri.isEmpty()) { + Log.debug("no Shaper set for loading resources ..."); + return; + } + this.config = ResourceConfigFile.create(this.uri); + if (this.config != null) { + this.confIdPaddingOut[GuiShape.SHAPER_POS_LEFT] = this.config.request("padding-out-left"); + this.confIdPaddingOut[GuiShape.SHAPER_POS_RIGHT] = this.config.request("padding-out-right"); + this.confIdPaddingOut[GuiShape.SHAPER_POS_TOP] = this.config.request("padding-out-top"); + this.confIdPaddingOut[GuiShape.SHAPER_POS_BOTTOM] = this.config.request("padding-out-buttom"); + this.confIdPaddingIn[GuiShape.SHAPER_POS_LEFT] = this.config.request("padding-in-left"); + this.confIdPaddingIn[GuiShape.SHAPER_POS_RIGHT] = this.config.request("padding-in-right"); + this.confIdPaddingIn[GuiShape.SHAPER_POS_TOP] = this.config.request("padding-in-top"); + this.confIdPaddingIn[GuiShape.SHAPER_POS_BOTTOM] = this.config.request("padding-in-buttom"); + this.confIdChangeTime = this.config.request("change-time"); + this.confProgramFileVert = this.config.request("program-vert"); + this.confProgramFileFrag = this.config.request("program-frag"); + this.confObjectFile = this.config.request("object-file"); + this.confIdImagePaletteFile = this.config.request("image-palette"); + this.confIdImagePaletteMode = this.config.request("image-palette-load-mode"); + } + String objectFile = this.config.getString(this.confObjectFile); + if (!objectFile.isEmpty()) { + this.shape = ResourceStaticMeshObjBynamic.create(Uri.valueOf(objectFile)); + this.verticesToModify = this.shape.getVertices(); + float top = 0; + float bottom = 0; + float left = 0; + float right = 0; + float back = 0; + float font = 0; + // estimate size of border: + for (int iii = 0; iii < this.verticesToModify.length - 2; iii += 3) { + left = Math.min(left, this.verticesToModify[iii]); + right = Math.max(right, this.verticesToModify[iii]); + top = Math.min(top, this.verticesToModify[iii + 1]); + bottom = Math.max(bottom, this.verticesToModify[iii + 1]); + back = Math.min(back, this.verticesToModify[iii + 2]); + font = Math.max(font, this.verticesToModify[iii + 2]); + } + this.sizeObject = new Padding(Math.abs(left), Math.abs(top), Math.abs(right), Math.abs(bottom)); + } + String paletteMode = this.config.getString(this.confIdImagePaletteMode, "linear"); + String paletteFile = this.config.getString(this.confIdImagePaletteFile); + if (!paletteFile.isEmpty()) { + this.resourceTexture = ResourceTextureFile.create(Uri.valueOf(paletteFile)); + if (paletteMode.equals("nearest")) { + this.resourceTexture.setFilterMode(TextureFilter.NEAREST); + } else { + this.resourceTexture.setFilterMode(TextureFilter.LINEAR); + } + } + String basicShaderFileVert = this.config.getString(this.confProgramFileVert); + String basicShaderFileFrag = this.config.getString(this.confProgramFileFrag); + if (!basicShaderFileVert.isEmpty() && !basicShaderFileFrag.isEmpty()) { + this.oGLprogram = ResourceProgram.create(Uri.valueOf(basicShaderFileVert), Uri.valueOf(basicShaderFileFrag)); + if (this.oGLprogram != null) { + this.oGLMatrixTransformation = this.oGLprogram.getUniform("in_matrixTransformation"); + this.oGLMatrixProjection = this.oGLprogram.getUniform("in_matrixProjection"); + this.oGLMatrixView = this.oGLprogram.getUniform("in_matrixView"); + // for the texture ID : + this.oGLtexID = this.oGLprogram.getUniform("in_textureBase"); + } + } + } + + /** + * @brief Same as the widfget periodic call (this is for change display) + * @param event The current time of the call. + * @return true The widget must call this fuction periodicly (and redraw itself) + * @return false No need to request the periodic call. + */ + public boolean periodicCall(final EventTime event) { + Log.verbose("call=" + event + "state transition=" + this.stateTransition + " speedTime=" + this.config.getNumber(this.confIdChangeTime)); + return true; + } + + /** + * @brief Set activate state of the element + * @param _status New activate status + */ + public void setActivateState(final int status) { + this.stateActivate = status; + } + + // @previous + public void setShape(final Vector2f origin, final Vector2f size) { + Padding tmp = getPadding(); + setShape(origin, size, origin.add(tmp.left(), tmp.bottom()), size.less(tmp.x(), tmp.y())); + } + + /** + * @brief set the shape property: + * + * ******************************************************************************** + * * _size * + * * * + * * * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - * * + * * * + * * | | * + * * *************************************************** * + * * | * * | * + * * * * * + * * | * * - - - - - - - - - - - - - - - - - - * * | * + * * * _insideSize * * + * * | * | | * | * + * * * * * + * * | * | | * | * + * * * * * + * * | * | | * | * + * * * * * + * * | * | | * | * + * * * * * + * * | * | | * | * + * * * * * + * * | * | | * | * + * * * _insidePos * * + * * | * * - - - - - - - - - - - - - - - - - - * * | * + * * * * * + * * | *************************************************** | * + * * * + * * | | * + * * * + * * * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - * * + * * * + * * * + * ******************************************************************************** + * _origin + * + * + * @param center Center of the object + * @param size Size of the display + */ + public void setShape(final Vector2f origin, final Vector2f size, final Vector2f insidePos, final Vector2f insideSize) { + //Log.error("Set shape property : origin=" + origin + " size=" + size + " in-pos=" + insidePos + " in-size=" + insideSize); + Vector2f halfSize = insideSize.multiply(0.5f); + float[] newVertices = Arrays.copyOf(this.verticesToModify, this.verticesToModify.length); + for (int iii = 0; iii < newVertices.length - 2; iii += 3) { + if (newVertices[iii] <= 0.0f) { + newVertices[iii] -= halfSize.x(); + } else { + newVertices[iii] += halfSize.x(); + } + if (newVertices[iii + 1] <= 0.0f) { + newVertices[iii + 1] -= halfSize.y(); + } else { + newVertices[iii + 1] += halfSize.y(); + } + } + this.transform = Matrix4f.createMatrixTranslate(new Vector3f(origin.x() + size.x() * 0.5f, origin.y() + size.y() * 0.5f, 0.0f)); + this.shape.setVertices(newVertices); + this.shape.flush(); + } + + public void setShape(final Vector3f origin, final Vector3f size) { + Padding tmp = getPadding(); + setShape(origin, size, origin.add(tmp.left(), tmp.bottom(), 0), size.less(tmp.x(), tmp.y(), 0)); + } + + public void setShape(final Vector3f origin, final Vector3f size, final Vector3f insidePos, final Vector3f insideSize) { + Vector3f halfSize = insideSize.multiply(0.5f); + float[] newVertices = Arrays.copyOf(this.verticesToModify, this.verticesToModify.length); + for (int iii = 0; iii < newVertices.length - 2; iii += 3) { + if (newVertices[iii] <= 0.0f) { + newVertices[iii] -= halfSize.x(); + } else { + newVertices[iii] += halfSize.x(); + } + if (newVertices[iii + 1] <= 0.0f) { + newVertices[iii + 1] -= halfSize.y(); + } else { + newVertices[iii + 1] += halfSize.y(); + } + if (newVertices[iii + 2] <= 0.0f) { + newVertices[iii + 2] -= halfSize.z(); + } else { + newVertices[iii + 2] += halfSize.z(); + } + } + this.transform = Matrix4f.createMatrixTranslate(new Vector3f(origin.x() + size.x() * 0.5f, origin.y() + size.y() * 0.5f, origin.z() + size.z() * 0.5f)); + this.shape.setVertices(newVertices); + } + + /** + * @brief change the shaper Source + * @param _uri New file of the shaper + */ + public void setSource(final Uri uri) { + clear(); + unLoadProgram(); + this.uri = uri; + loadProgram(); + } + + /** + * @brief Change the current state + * @param _newState Current state of the configuration + * @return true Need redraw. + * @return false No need redraw. + */ + public boolean setState(final int newState) { + if (this.stateActivate == newState) { + return false; + } + this.stateActivate = newState; + return true; + } + + /** + * @brief Un-Load the openGL program and get all the ID needed + */ + + private void unLoadProgram() { + this.oGLprogram = null; + this.resourceTexture = null; + this.config = null; + for (int iii = 0; iii < 4; ++iii) { + this.confIdPaddingOut[iii] = -1; + this.confIdPaddingIn[iii] = -1; + } + this.confIdChangeTime = -1; + this.listAssiciatedId.clear(); + } +} diff --git a/src/org/atriasoft/ewol/compositing/Shaper.cpp b/src/org/atriasoft/ewol/compositing/Shaper.cpp new file mode 100644 index 0000000..2067183 --- /dev/null +++ b/src/org/atriasoft/ewol/compositing/Shaper.cpp @@ -0,0 +1,445 @@ +/** @file + * @author Edouard DUPIN + * @copyright 2011, Edouard DUPIN, all right reserved + * @license MPL v2.0 (see license file) + */ + +#include +#include +#include +#include +ETK_DECLARE_TYPE(ewol::compositing::Shaper); + +// VBO table property: +const int32_t ewol::compositing::Shaper::m_vboIdCoord(0); +const int32_t ewol::compositing::Shaper::m_vboIdPos(1); +#define NB_VBO (2) + +ewol::compositing::Shaper::Shaper(const etk::Uri& _uri) : + m_uri(_uri), + m_config(null), + m_confIdMode(-1), + m_confIdDisplayOutside(-1), + m_confIdChangeTime(-1), + m_confProgramFile(-1), + m_confColorFile(-1), + m_confImageFile(-1), + m_GLprogram(null), + m_GLPosition(-1), + m_GLMatrix(-1), + m_GLStateActivate(-1), + m_GLStateOld(-1), + m_GLStateNew(-1), + m_GLStateTransition(-1), + m_resourceTexture(null), + m_nextStatusRequested(-1), + m_propertyOrigin(0,0), + m_propertySize(0,0), + m_propertyInsidePosition(0,0), + m_propertyInsideSize(0,0), + m_stateActivate(0), + m_stateOld(0), + m_stateNew(0), + m_stateTransition(1.0), + m_nbVertexToDisplay(0) { + for (size_t iii=0; iiisetName("[VBO] of ewol::compositing::Shaper"); + loadProgram(); +} + +ewol::compositing::Shaper::~Shaper() { + unLoadProgram(); +} + +void ewol::compositing::Shaper::unLoadProgram() + +void ewol::compositing::Shaper::loadProgram() + +void ewol::compositing::Shaper::draw(bool _disableDepthTest) +void ewol::compositing::Shaper::clear() + +bool ewol::compositing::Shaper::setState(int32_t _newState) + +bool ewol::compositing::Shaper::changeStatusIn(int32_t _newStatusId) + +bool ewol::compositing::Shaper::periodicCall(const ewol::event::Time& _event) + +//Create Line: +void ewol::compositing::Shaper::addVertexLine(float _yTop, + float _yButtom, + float _x1, + float _x2, + float _x3, + float _x4, + float _x5, + float _x6, + float _x7, + float _x8, + float _yValTop, + float _yValButtom, + const float* _table, + bool _displayOutside) { + if (m_nbVertexToDisplay != 0) { + // change line ... + m_VBO->pushOnBuffer(m_vboIdCoord, + m_VBO->getOnBufferVec2(m_vboIdCoord, m_nbVertexToDisplay-1)); + m_VBO->pushOnBuffer(m_vboIdPos, + m_VBO->getOnBufferVec2(m_vboIdPos, m_nbVertexToDisplay-1)); + + m_nbVertexToDisplay++; + if (_displayOutside == true) { + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x1, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[0],_yValButtom)); + m_nbVertexToDisplay++; + } else { + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x2, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[1],_yValButtom)); + m_nbVertexToDisplay++; + } + } + + if (_displayOutside == true) { + // A + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x1, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[0],_yValButtom)); + m_nbVertexToDisplay++; + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x1, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[0],_yValTop)); + m_nbVertexToDisplay++; + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x2, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[1],_yValButtom)); + m_nbVertexToDisplay++; + // B + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x2, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[1],_yValTop)); + m_nbVertexToDisplay++; + + // C + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x3, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[2],_yValButtom)); + m_nbVertexToDisplay++; + } else { + // C + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x2, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[1],_yValButtom)); + m_nbVertexToDisplay++; + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x2, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[1],_yValTop)); + m_nbVertexToDisplay++; + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x3, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[2],_yValButtom)); + m_nbVertexToDisplay++; + } + // D + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x3, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[2],_yValTop)); + m_nbVertexToDisplay++; + + // E + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x4, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[3],_yValButtom)); + m_nbVertexToDisplay++; + // F + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x4, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[3],_yValTop)); + m_nbVertexToDisplay++; + + // G + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x5, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[4],_yValButtom)); + m_nbVertexToDisplay++; + // H + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x5, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[4],_yValTop)); + m_nbVertexToDisplay++; + + // I + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x6, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[5],_yValButtom)); + m_nbVertexToDisplay++; + // J + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x6, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[5],_yValTop)); + m_nbVertexToDisplay++; + + // K + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x7, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[6],_yValButtom)); + m_nbVertexToDisplay++; + // L + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x7, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[6],_yValTop)); + m_nbVertexToDisplay++; + + if (_displayOutside == true) { + // M + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x8, _yButtom)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[7],_yValButtom)); + m_nbVertexToDisplay++; + // N + m_VBO->pushOnBuffer(m_vboIdCoord, vec2(_x8, _yTop)); + m_VBO->pushOnBuffer(m_vboIdPos, vec2(_table[7],_yValTop)); + m_nbVertexToDisplay++; + } +} +const float modeDisplay[][8] = { + /* !! 0 !! + * / ******* + * / ****** / + * ****** / + */ + { 0.0f, 0.0f, 0.5f, 0.5f, 0.5f, 0.5f, 1.0f, 1.0f }, + /* !! 1 !! + * ****** \ + * \ ****** \ + * \ ******* + */ + { 1.0f, 1.0f, 0.5f, 0.5f, 0.5f, 0.5f, 0.0f, 0.0f }, + /* !! 2 !! + * / ****** \ + * ****** / \ ******* + */ + { 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f }, + /* !! 3 !! + * ****** \ / ******* + * \ ****** / + */ + { 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 1.0f }, + /* !! 4 !! + * / ******* + * / ****** / + * ****** / + */ + { -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 1.0f }, + /* !! 5 !! + * ****** \ + * \ ****** \ + * \ ******* + */ + { 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, -1.0f, -1.0f }, + /* !! 6 !! + * / ****** \ + * ****** / \ ******* + */ + { -1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f, -1.0f, -1.0f }, + /* !! 7 !! + * ****** \ / ******* + * \ ****** / + */ + { 1.0f, 1.0f, -1.0f, -1.0f, -1.0f, -1.0f, 1.0f, 1.0f } +}; + +void ewol::compositing::Shaper::setShape(const vec2& _origin, const vec2& _size, const vec2& _insidePos, const vec2& _insideSize) { + m_VBO->clear(); + ewol::Padding borderTmp = getBorder(); + ewol::Padding paddingIn = getPaddingIn(); + ewol::Padding paddingOut = getPaddingOut(); + ewol::Padding padding = paddingIn + borderTmp + paddingOut; + ewol::Padding enveloppe(_origin.x(), + _origin.y() + _size.y(), + _origin.x() + _size.x(), + _origin.y()); + #if 0 + ewol::Padding inside(_insidePos.x(), + _insidePos.y() + _insideSize.y(), + _insidePos.x() + _insideSize.x(), + _insidePos.y()); + ewol::Padding insideBorder(inside.xLeft() - paddingIn.xLeft(), + inside.yTop() + paddingIn.yTop(), + inside.xRight() + paddingIn.xRight(), + inside.yButtom() - paddingIn.yButtom()); + ewol::Padding border(insideBorder.xLeft() - borderTmp.xLeft(), + insideBorder.yTop() + borderTmp.yTop(), + insideBorder.xRight() + borderTmp.xRight(), + insideBorder.yButtom() - borderTmp.yButtom()); + #else + ewol::Padding border(_insidePos.x() - padding.xLeft() + paddingOut.xLeft(), + _insidePos.y() + _insideSize.y() + padding.yTop() - paddingOut.yTop(), + _insidePos.x() + _insideSize.x() + padding.xRight() - paddingOut.xRight(), + _insidePos.y() - padding.yButtom() + paddingOut.yButtom()); + ewol::Padding insideBorder(border.xLeft() + borderTmp.xLeft(), + border.yTop() - borderTmp.yTop(), + border.xRight() - borderTmp.xRight(), + border.yButtom() + borderTmp.yButtom()); + ewol::Padding inside(insideBorder.xLeft() + etk::max(0.0f, paddingIn.xLeft()), + insideBorder.yTop() - etk::max(0.0f, paddingIn.yTop()), + insideBorder.xRight() - etk::max(0.0f, paddingIn.xRight()), + insideBorder.yButtom() + etk::max(0.0f, paddingIn.yButtom())); + + #endif + /* + EWOL_ERROR(" enveloppe = " << enveloppe); + EWOL_ERROR(" border = " << border); + EWOL_ERROR(" inside = " << inside); + */ + int32_t mode = 0; + bool displayOutside = false; + if (m_config != null) { + mode = m_config->getNumber(m_confIdMode); + displayOutside = m_config->getBoolean(m_confIdDisplayOutside); + } + m_nbVertexToDisplay = 0; + if (displayOutside == true) { + addVertexLine(enveloppe.yTop(), border.yTop(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][7], modeDisplay[mode][6], + modeDisplay[mode], + displayOutside); + } + addVertexLine(border.yTop(), insideBorder.yTop(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][6], modeDisplay[mode][5], + modeDisplay[mode], + displayOutside); + addVertexLine(insideBorder.yTop(), inside.yTop(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][5], modeDisplay[mode][4], + modeDisplay[mode], + displayOutside); + addVertexLine(inside.yTop(), inside.yButtom(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][4], modeDisplay[mode][3], + modeDisplay[mode], + displayOutside); + addVertexLine(inside.yButtom(), insideBorder.yButtom(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][3], modeDisplay[mode][2], + modeDisplay[mode], + displayOutside); + addVertexLine(insideBorder.yButtom(), border.yButtom(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][2], modeDisplay[mode][1], + modeDisplay[mode], + displayOutside); + if (displayOutside == true) { + addVertexLine(border.yButtom(), enveloppe.yButtom(), + enveloppe.xLeft(), + border.xLeft(), + insideBorder.xLeft(), + inside.xLeft(), + inside.xRight(), + insideBorder.xRight(), + border.xRight(), + enveloppe.xRight(), + modeDisplay[mode][1], modeDisplay[mode][0], + modeDisplay[mode], + displayOutside); + } + m_VBO->flush(); +} + +ewol::Padding ewol::compositing::Shaper::getPadding() + +ewol::Padding ewol::compositing::Shaper::getPaddingIn() + +ewol::Padding ewol::compositing::Shaper::getPaddingOut() + +ewol::Padding ewol::compositing::Shaper::getBorder() + +void ewol::compositing::Shaper::setSource(const etk::Uri& _uri) + +bool ewol::compositing::Shaper::hasSources() + +const etk::Color& ewol::compositing::Shaper::getColor(int32_t _id) { + static const etk::Color errorValue(0,0,0,0); + if (m_colorProperty == null) { + EWOL_WARNING("null of m_colorProperty ==> return #0000 for id " << _id); + return errorValue; + } + return m_colorProperty->get(_id); +} + +int32_t ewol::compositing::Shaper::requestColor(const etk::String& _name) { + if (m_colorProperty == null) { + EWOL_WARNING("null of m_colorProperty ==> return -1 for name " << _name); + return -1; + } + return m_colorProperty->request(_name); +} + +int32_t ewol::compositing::Shaper::requestConfig(const etk::String& _name) { + if (m_config == null) { + EWOL_WARNING("null of m_config ==> return -1 for name " << _name); + return -1; + } + return m_config->request(_name); +} + +double ewol::compositing::Shaper::getConfigNumber(int32_t _id) { + if ( _id == -1 + || m_config == null) { + EWOL_WARNING("null of m_config ==> return 0.0 for id " << _id); + return 0.0; + } + return m_config->getNumber(_id); +} + + +namespace etk { + template<> etk::String toString(const ewol::compositing::Shaper& _obj) { + return _obj.getSource().get(); + } + template<> etk::UString toUString(const ewol::compositing::Shaper& _obj) { + return etk::toUString(etk::toString(_obj)); + } + template<> bool from_string(ewol::compositing::Shaper& _variableRet, const etk::String& _value) { + _variableRet.setSource(_value); + return true; + } + template<> bool from_string(ewol::compositing::Shaper& _variableRet, const etk::UString& _value) { + return from_string(_variableRet, etk::toString(_value)); + } +}; \ No newline at end of file diff --git a/src/org/atriasoft/ewol/compositing/TextBase.java b/src/org/atriasoft/ewol/compositing/TextBase.java index ab049e5..a240bd3 100644 --- a/src/org/atriasoft/ewol/compositing/TextBase.java +++ b/src/org/atriasoft/ewol/compositing/TextBase.java @@ -51,7 +51,9 @@ public abstract class TextBase extends Compositing { protected FontMode mode = FontMode.REGULAR; // !< font display property : Regular/Bold/Italic/BoldItalic protected int nbCharDisplayed; // !< prevent some error in calculation size. protected boolean needDisplay; // !< This just need the display and not the size rendering. - protected int oGLMatrix = -1; // !< openGL id on the element (transformation matrix) + protected int oGLMatrixProjection = -1; //!< openGL id on the element (Projection matrix) + protected int oGLMatrixTransformation = -1; //!< openGL id on the element (transformation matrix) + protected int oGLMatrixView = -1; //!< openGL id on the element (view matrix) protected ResourceProgram oGLprogram; // !< pointer on the opengl display program protected int oGLtexID = -1; // !< openGL id on the element (texture ID) protected int oGLtextHeight = -1; // !< openGL Id on the texture height @@ -370,7 +372,9 @@ public abstract class TextBase extends Compositing { ResourceProgram old = this.oGLprogram; this.oGLprogram = ResourceProgram.create(vertexShader, fragmentShader); if (this.oGLprogram != null) { - this.oGLMatrix = this.oGLprogram.getUniform("in_MatrixTransformation"); + this.oGLMatrixTransformation = this.oGLprogram.getUniform("in_matrixTransformation"); + this.oGLMatrixProjection = this.oGLprogram.getUniform("in_matrixProjection"); + this.oGLMatrixView = this.oGLprogram.getUniform("in_matrixView"); this.oGLtexID = this.oGLprogram.getUniform("in_texID"); this.oGLtextWidth = this.oGLprogram.getUniform("in_texWidth"); this.oGLtextHeight = this.oGLprogram.getUniform("in_texHeight"); @@ -1037,7 +1041,7 @@ public abstract class TextBase extends Compositing { public void setPos(final Vector3f pos) { // check min max for display area if (this.nbCharDisplayed != 0) { - Log.verbose("update size 1 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); + //Log.verbose("update size 1 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); this.sizeDisplayStop = Vector3f.max(this.position, this.sizeDisplayStop); this.sizeDisplayStart = Vector3f.min(this.position, this.sizeDisplayStart); } @@ -1049,12 +1053,12 @@ public abstract class TextBase extends Compositing { if (this.nbCharDisplayed == 0) { this.sizeDisplayStart = this.position; this.sizeDisplayStop = this.position.withY(this.sizeDisplayStop.y() + getHeight()); - Log.verbose("update size 0 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); + //Log.verbose("update size 0 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); } else { - Log.verbose("update size 3 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); + //Log.verbose("update size 3 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); this.sizeDisplayStop = Vector3f.max(this.position, this.sizeDisplayStop); this.sizeDisplayStart = Vector3f.min(this.position, this.sizeDisplayStart); - Log.verbose("update size 4 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); + //Log.verbose("update size 4 " + this.sizeDisplayStart + " " + this.sizeDisplayStop); } } diff --git a/src/org/atriasoft/ewol/context/ConfigFont.java b/src/org/atriasoft/ewol/context/ConfigFont.java deleted file mode 100644 index 13af4b1..0000000 --- a/src/org/atriasoft/ewol/context/ConfigFont.java +++ /dev/null @@ -1,82 +0,0 @@ -package org.atriasoft.ewol.context; - -import java.util.HashMap; -import java.util.Map; - -import org.atriasoft.etk.Uri; -import org.atriasoft.ewol.internal.Log; - -/** @file - * @author Edouard DUPIN - * @copyright 2011, Edouard DUPIN, all right reserved - * @license MPL v2.0 (see license file) - */ - -public class ConfigFont { - private final Map fonts = new HashMap<>(); - private String name = "FreeSherif"; - private int size = 12; - - /** - * Constructor - */ - public ConfigFont() { - // add default Esvg fonts: - this.fonts.put("FreeSherif", new Uri("FONTS", "FreeSherif.svg", "esvg")); - this.fonts.put("FreeSans", new Uri("FONTS", "FreeSans.svg", "esvg")); - this.fonts.put("FreeMono", new Uri("FONTS", "FreeMono.svg", "esvg")); - } - - public Uri getFontUri(final String fontName) { - Uri out = this.fonts.get(fontName); - if (out == null) { - Log.warning(" try to get unexistant font : " + fontName); - } - return out; - } - - /** - * get the current default font name - * @return a reference on the font name string - */ - public String getName() { - return this.name; - } - - /** - * get the default font size. - * @return the font size. - */ - public int getSize() { - return this.size; - } - - /** - * set the defaut font for all the widgets and basics display. - * @param fontName The font name requested (not case sensitive) ex "Arial" or multiple separate by ';' ex : "Arial;Helvetica". - * @param size The default size of the font default=10. - */ - public void set(final String fontName, final int size) { - this.name = fontName; - this.size = size; - Log.debug("Set default Font : '" + this.name + "' size=" + this.size); - } - - /** - * Set the current default font name - * @param fontName The font name requested (not case sensitive) ex "Arial" or multiple separate by ';' ex : "Arial;Helvetica". - */ - public void setName(final String fontName) { - this.name = fontName; - Log.debug("Set default Font : '" + this.name + "' size=" + this.size + " (change name only)"); - } - - /** - * Set the default font size. - * @param size new font size. - */ - public void setSize(final int size) { - this.size = size; - Log.debug("Set default Font : '" + this.name + "' size=" + this.size + " (change size only)"); - } -} diff --git a/src/org/atriasoft/ewol/context/EwolContext.java b/src/org/atriasoft/ewol/context/EwolContext.java index e3a19aa..a85e737 100644 --- a/src/org/atriasoft/ewol/context/EwolContext.java +++ b/src/org/atriasoft/ewol/context/EwolContext.java @@ -45,8 +45,6 @@ public class EwolContext extends GaleApplication { private EwolApplication application; // !< Application handle - private final ConfigFont configFont = new ConfigFont(); // !< global font configuration - private final int initStepId = 0; private final int initTotalStep = 0; @@ -93,10 +91,6 @@ public class EwolContext extends GaleApplication { return this.objectManager; } - public ConfigFont getFontDefault() { - return this.configFont; - } - public ResourceManager getResourcesManager() { return Gale.getContext().getResourcesManager(); } @@ -225,7 +219,7 @@ public class EwolContext extends GaleApplication { @Override public void onKeyboard(final KeySpecial special, final KeyKeyboard type, final Character value, final KeyStatus state) { - Log.verbose("event {" + special + "} " + type + " " + value + " " + state); + Log.verbose("event {" + special + "} " + type + " '" + value + "' " + state); // store the keyboard special key status for mouse event... this.input.setLastKeyboardSpecial(special); if (this.windowsCurrent == null) { @@ -262,9 +256,9 @@ public class EwolContext extends GaleApplication { } else { // THREADKEYBORADMOVE final EntrySystem tmpEntryEvent; if (isDown) { - tmpEntryEvent = new EntrySystem(KeyKeyboard.CHARACTER, KeyStatus.down, special, null); + tmpEntryEvent = new EntrySystem(type, KeyStatus.down, special, null); } else { - tmpEntryEvent = new EntrySystem(KeyKeyboard.CHARACTER, KeyStatus.up, special, null); + tmpEntryEvent = new EntrySystem(type, KeyStatus.up, special, null); } tmpWidget.systemEventEntry(tmpEntryEvent); } @@ -301,7 +295,8 @@ public class EwolContext extends GaleApplication { this.objectManager.timeCall(time); } - public void onPointer(final KeyType type, final int pointerID, final Vector2f pos, final KeyStatus state) { + @Override + public void onPointer(final KeySpecial special, final KeyType type, final int pointerID, final Vector2f pos, final KeyStatus state) { switch (state) { case move: // Log.debug("Receive MSG : THREAD_INPUT_MOTION"); @@ -332,7 +327,7 @@ public class EwolContext extends GaleApplication { return; } // Redraw all needed elements - window.onRegenerateDisplay(); + window.systemRegenerateDisplay(); if (this.widgetManager.isDrawingNeeded()) { markDrawingIsNeeded(); } diff --git a/src/org/atriasoft/ewol/context/InputManager.java b/src/org/atriasoft/ewol/context/InputManager.java index 4626208..a5179cc 100644 --- a/src/org/atriasoft/ewol/context/InputManager.java +++ b/src/org/atriasoft/ewol/context/InputManager.java @@ -170,13 +170,13 @@ class InputManager { // this event is all time on the good widget ... and manage the enter and leave ... // NOTE : the "layer widget" force us to get the widget at the specific position all the time : Widget tmpWidget = null; - if (this.grabWidget.get() != null) { + if (this.grabWidget != null && this.grabWidget.get() != null) { // grab all events ... tmpWidget = this.grabWidget.get(); } else if (tmpWindows != null) { tmpWidget = tmpWindows.getWidgetAtPos(pos); } - if (tmpWidget != eventTable[pointerID].curentWidgetEvent.get() + if (eventTable[pointerID].curentWidgetEvent != null && tmpWidget != eventTable[pointerID].curentWidgetEvent.get() || (eventTable[pointerID].isInside && (eventTable[pointerID].origin.x() > pos.x() || eventTable[pointerID].origin.y() > pos.y() || (eventTable[pointerID].origin.x() + eventTable[pointerID].size.x()) < pos.x() || (eventTable[pointerID].origin.y() + eventTable[pointerID].size.y()) < pos.y()))) { eventTable[pointerID].isInside = false; @@ -301,7 +301,7 @@ class InputManager { eventTable[pointerID].lastTimeEvent = currentTime; // set the element inside ... eventTable[pointerID].isInside = true; - Widget tmpWidget = this.grabWidget.get(); + Widget tmpWidget = this.grabWidget == null ? null : this.grabWidget.get(); // get destination widget : if (tmpWindows != null) { if (tmpWidget != null && type == KeyType.mouse) { @@ -368,7 +368,7 @@ class InputManager { nbClickMax = 5; } // in grab mode the single to quinte event are not generated .... - if ((this.grabWidget.get() == null || type != KeyType.mouse) && eventTable[pointerID].nbClickEvent < nbClickMax) { + if ((this.grabWidget == null || this.grabWidget.get() == null || type != KeyType.mouse) && eventTable[pointerID].nbClickEvent < nbClickMax) { // generate event SINGLE : eventTable[pointerID].nbClickEvent++; //Log.debug("GUI : Input ID=" + pointerID + " == >" + eventTable[pointerID].destinationInputId + " [" + eventTable[pointerID].nbClickEvent + "] " + pos); diff --git a/src/org/atriasoft/ewol/event/EntrySystem.java b/src/org/atriasoft/ewol/event/EntrySystem.java index cba6dd0..661c9b7 100644 --- a/src/org/atriasoft/ewol/event/EntrySystem.java +++ b/src/org/atriasoft/ewol/event/EntrySystem.java @@ -4,6 +4,7 @@ import org.atriasoft.gale.key.KeyKeyboard; import org.atriasoft.gale.key.KeySpecial; import org.atriasoft.gale.key.KeyStatus; +@SuppressWarnings("preview") public record EntrySystem( EventEntry event) { public EntrySystem(final EventEntry event) { diff --git a/src/org/atriasoft/ewol/resource/ResourceConfigFile.java b/src/org/atriasoft/ewol/resource/ResourceConfigFile.java index 281969e..3528b4e 100644 --- a/src/org/atriasoft/ewol/resource/ResourceConfigFile.java +++ b/src/org/atriasoft/ewol/resource/ResourceConfigFile.java @@ -32,30 +32,35 @@ public class ResourceConfigFile extends Resource { * @param name Name of the configuration file. * @return pointer on the resource or null if an error occurred. */ - public static ResourceConfigFile keep(final String name) { + @SuppressWarnings("preview") + public static ResourceConfigFile create(final Uri name) { Resource resource2 = null; - if (!name.isEmpty() && !name.contentEquals("---")) { + if (name != null && !name.isEmpty()) { resource2 = Resource.getManager().localKeep(name); } if (resource2 != null) { - if (resource2 instanceof ResourceConfigFile) { + if (resource2 instanceof ResourceConfigFile tmpp) { resource2.keep(); - return (ResourceConfigFile) resource2; + return tmpp; } Log.critical("Request resource file : '" + name + "' With the wrong type (dynamic cast error)"); return null; } - final ResourceConfigFile resource = new ResourceConfigFile(Uri.valueOf(name)); + final ResourceConfigFile resource = new ResourceConfigFile(name); Resource.getManager().localAdd(resource); return resource; } + public static ResourceConfigFile keep(final String name) { + return ResourceConfigFile.create(Uri.valueOf(name)); + } + // List of all color in the file private final List list = new ArrayList<>(); protected ResourceConfigFile(final Uri uri) { - super(uri.get()); + super(uri.toString()); Log.debug("SFP : load '" + uri + "'"); reload(); @@ -67,7 +72,7 @@ public class ResourceConfigFile extends Resource { } - boolean getBoolean(final int id) { + public boolean getBoolean(final int id) { if (id < 0 || this.list.get(id).node == null || !this.list.get(id).node.isJsonBoolean()) { return false; } @@ -81,9 +86,13 @@ public class ResourceConfigFile extends Resource { return this.list.get(id).node.toJsonNumber().getValue(); } - String getString(final int id) { + public String getString(final int id) { + return getString(id, ""); + } + + public String getString(final int id, final String defaultValue) { if (id < 0 || this.list.get(id).node == null || !this.list.get(id).node.isJsonString()) { - return ""; + return defaultValue; } return this.list.get(id).node.toJsonString().getValue(); } diff --git a/src/org/atriasoft/ewol/resource/ResourceFontSvg.java b/src/org/atriasoft/ewol/resource/ResourceFontSvg.java index 56507e6..811c07d 100644 --- a/src/org/atriasoft/ewol/resource/ResourceFontSvg.java +++ b/src/org/atriasoft/ewol/resource/ResourceFontSvg.java @@ -5,8 +5,8 @@ */ package org.atriasoft.ewol.resource; -import org.atriasoft.egami.Image; -import org.atriasoft.egami.ImageMono; +import org.atriasoft.egami.ImageByte; +import org.atriasoft.egami.ImageByteMono; import org.atriasoft.esvg.EsvgFont; import org.atriasoft.esvg.font.Glyph; import org.atriasoft.esvg.render.Weight; @@ -63,7 +63,7 @@ public class ResourceFontSvg extends Resource { Log.info(" number of glyph = " + this.font.getNumGlyphs()); } - public synchronized boolean drawGlyph(final Image imageOut, final int fontSize, final Vector2i glyphPosition, final GlyphProperty property, final int posInImage) { + public synchronized boolean drawGlyph(final ImageByte imageOut, final int fontSize, final Vector2i glyphPosition, final GlyphProperty property, final int posInImage) { Weight weight = this.font.render(property.glyph.getUnicodeValue(), fontSize); if (weight == null) { return false; @@ -75,16 +75,16 @@ public class ResourceFontSvg extends Resource { switch (posInImage) { default: case 0: - imageOut.setA(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); + imageOut.setAFloat(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); break; case 1: - imageOut.setR(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); + imageOut.setRFloat(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); break; case 2: - imageOut.setG(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); + imageOut.setGFloat(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); break; case 3: - imageOut.setB(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); + imageOut.setBFloat(glyphPosition.x() + xxx, glyphPosition.y() + yyy, valueColor); break; } } @@ -92,7 +92,7 @@ public class ResourceFontSvg extends Resource { return true; } - public synchronized boolean drawGlyph(final ImageMono imageOut, final int fontSize, final GlyphProperty property, final int borderSize) { + public synchronized boolean drawGlyph(final ImageByteMono imageOut, final int fontSize, final GlyphProperty property, final int borderSize) { Weight weight = this.font.render(property.glyph.getUnicodeValue(), fontSize); for (int jjj = 0; jjj < weight.getHeight(); jjj++) { for (int iii = 0; iii < weight.getWidth(); iii++) { diff --git a/src/org/atriasoft/ewol/resource/ResourceTexture2.java b/src/org/atriasoft/ewol/resource/ResourceTexture2.java index 2decc05..b0f484c 100644 --- a/src/org/atriasoft/ewol/resource/ResourceTexture2.java +++ b/src/org/atriasoft/ewol/resource/ResourceTexture2.java @@ -6,7 +6,8 @@ package org.atriasoft.ewol.resource; import org.atriasoft.echrono.Steady; -import org.atriasoft.egami.Image; +import org.atriasoft.egami.ImageByte; +import org.atriasoft.egami.ImageByteRGBA; import org.atriasoft.etk.Uri; import org.atriasoft.etk.math.Vector2i; import org.atriasoft.ewol.internal.Log; @@ -42,11 +43,11 @@ public class ResourceTexture2 extends Resource { */ // openGl Context properties : - protected Image data = new Image(32, 32); + protected ImageByte data = new ImageByteRGBA(32, 32); // !< Color space of the image. private final TextureColorMode dataColorSpace = TextureColorMode.rgba; // Filter apply at the image when rendering it - protected TextureFilter filter = TextureFilter.linear; + protected TextureFilter filter = TextureFilter.LINEAR; // ! Last loaded size in the system openGL protected Vector2i lastSize = new Vector2i(1, 1); protected int lastSizeObject = 0; @@ -105,7 +106,7 @@ public class ResourceTexture2 extends Resource { } // Get the reference on this image to draw something on it ... - public Image get() { + public ImageByte get() { return this.data; } @@ -143,7 +144,7 @@ public class ResourceTexture2 extends Resource { * @note It will resize in square2 if needed by the system. * @param image Image to set. */ - public synchronized void set(final Image image) { + public synchronized void set(final ImageByte image) { Log.debug("Set a new image in a texture:"); Log.debug(" size=" + image.getSize()); this.data = image; @@ -197,7 +198,7 @@ public class ResourceTexture2 extends Resource { * TODO : use unlockable synchronized ... if (lock.tryLock() == false) { //Lock * error ==> try later ... return false; } */ - final int typeObject = OpenGL.GL_RGBA; + final int typeObject = this.data.hasAlpha() ? OpenGL.GL_RGBA : OpenGL.GL_RGB; final int sizeObject = OpenGL.GL_UNSIGNED_BYTE; if (this.loaded) { if (this.lastTypeObject != typeObject || this.lastSizeObject != sizeObject || !this.lastSize.equals(this.data.getSize())) { @@ -217,7 +218,7 @@ public class ResourceTexture2 extends Resource { Log.debug("TEXTURE: update [" + getId() + "]=" + this.data.getSize() + "=>" + this.data.getGPUSize() + " OGlId=" + this.texId + " type=" + this.data.getClass().getCanonicalName()); } // in all case we set the texture properties : - // TODO : check error ??? + // TODO check error ??? OpenGL.bindTexture2D(this.texId); if (!this.loaded) { @@ -226,7 +227,7 @@ public class ResourceTexture2 extends Resource { } else { OpenGL.setTexture2DWrapRepeat(); } - if (this.filter == TextureFilter.linear) { + if (this.filter == TextureFilter.LINEAR) { OpenGL.setTexture2DFilterLinear(); } else { OpenGL.setTexture2DFilterNearest(); @@ -235,26 +236,7 @@ public class ResourceTexture2 extends Resource { // glPixelStorei(GLUNPACKALIGNMENT,1); final Steady toc1 = Steady.now(); Log.verbose(" BIND ==> " + toc1.less(tic)); - // egami::store(this.data, String("~/texture") + etk::toString(getId()) + - // ".bmp"); - /* - * if (false) { // On some embended target, the texture size must be square of - * 2: if (this.loaded == false) { // 1: Create the square 2 texture: final int - * bufferSize = this.data.getGPUSize().x() * this.data.getGPUSize().y() * 8; - * static List tmpData; if (tmpData.size() < bufferSize) { - * tmpData.resize(bufferSize, 0.0f); } Log.debug(" CREATE texture ==> " + - * this.data.getGPUSize()); // 2 create a new empty texture: - * OpenGL.glTexImage2D(GLTEXTURE2D, // Target 0, // Level typeObject, // - * Format internal this.data.getGPUSize().x(), this.data.getGPUSize().y(), 0, // - * Border typeObject, // format sizeObject, // type tmpData[0] ); - * - * } //3 Flush all time the data: Steady tic1 = Steady.now(); - * glTexSubImage2D(GLTEXTURE2D, // Target 0, // Level 0, // x offset 0, // y - * offset this.data.getWidth(), this.data.getHeight(), typeObject, // format - * sizeObject, // type (void*)((char*)this.data.getTextureDataPointer()) ); - * Steady toc2 = Steady.now(); Log.info(" updateContext [STOP] ==> " + - * toc2.less(tic1)); } else - */ + // egami::store(this.data, String("~/texture") + etk::toString(getId()) + ".bmp"); if (!this.loaded) { OpenGL.glTexImage2D(0, // Level typeObject, // Format internal @@ -278,7 +260,3 @@ public class ResourceTexture2 extends Resource { return true; } } - -enum TextureFilter { - linear, nearest -} diff --git a/src/org/atriasoft/ewol/resource/ResourceTextureFile.java b/src/org/atriasoft/ewol/resource/ResourceTextureFile.java index 56165ca..b4e518f 100644 --- a/src/org/atriasoft/ewol/resource/ResourceTextureFile.java +++ b/src/org/atriasoft/ewol/resource/ResourceTextureFile.java @@ -5,13 +5,13 @@ */ package org.atriasoft.ewol.resource; -import org.atriasoft.egami.Egami; -import org.atriasoft.egami.Image; +import org.atriasoft.egami.ImageByte; import org.atriasoft.etk.Uri; import org.atriasoft.etk.math.Vector2i; import org.atriasoft.ewol.internal.Log; import org.atriasoft.ewol.internal.Tools; import org.atriasoft.gale.resource.Resource; +import org.atriasoft.iogami.IOgami; // TODO : Change tis file name ... @@ -82,13 +82,16 @@ public class ResourceTextureFile extends ResourceTexture2 { return object; } - protected ResourceTextureFile() { - } + protected ResourceTextureFile() {} protected ResourceTextureFile(final String genName, final Uri uri, final Vector2i size) { super(genName); Log.debug("create a new resource::Image : genName=" + genName + " uri=" + uri + " size=" + size); - final Image tmp = Egami.load(uri, size); + final ImageByte tmp = IOgami.load(uri, size); + if (tmp == null) { + Log.error("Can not load the file : " + uri); + return; + } set(tmp); } diff --git a/src/org/atriasoft/ewol/resource/TextureFilter.java b/src/org/atriasoft/ewol/resource/TextureFilter.java new file mode 100644 index 0000000..0aeae62 --- /dev/null +++ b/src/org/atriasoft/ewol/resource/TextureFilter.java @@ -0,0 +1,5 @@ +package org.atriasoft.ewol.resource; + +public enum TextureFilter { + LINEAR, NEAREST +} diff --git a/src/org/atriasoft/ewol/resource/font/GlyphProperty.java b/src/org/atriasoft/ewol/resource/font/GlyphProperty.java index 193e77b..1d4a8ce 100644 --- a/src/org/atriasoft/ewol/resource/font/GlyphProperty.java +++ b/src/org/atriasoft/ewol/resource/font/GlyphProperty.java @@ -51,13 +51,15 @@ public class GlyphProperty { public Vector2i sizeTexture = new Vector2i(10, 10); //!< size of the element to display public Vector2f texturePosSize = Vector2f.ZERO; //!< Texture normalized size (SIZE) public Vector2f texturePosStart = Vector2f.ZERO; //!< Texture normalized position (START) + public Vector2f textureRenderOffset = Vector2f.ZERO; //!< Offset to apply on the rendering to display glyph at the good position (correct position when render texture is bigger than the glyph size public GlyphProperty(final EsvgFont font, final Glyph glyph, final int fontSize) { this.glyph = glyph; this.charcode = this.glyph.getUnicodeValue(); this.fontSize = fontSize; this.sizeTexture = font.calculateWidthRendering(glyph.getUnicodeValue(), fontSize); - this.scaleFactor = font.calculateSclaeFactor(fontSize); + this.scaleFactor = font.calculateSclaleFactor(fontSize); + this.textureRenderOffset = font.calculateRenderOffset(fontSize); } public GlyphProperty(final EsvgFont font, final int charcode, final int fontSize) { @@ -83,6 +85,10 @@ public class GlyphProperty { return this.glyph.getHorizAdvX() * this.scaleFactor; } + public Vector2f getTextureRenderOffset() { + return this.textureRenderOffset; + } + public int getUnicodeValue() { return this.charcode; } diff --git a/src/org/atriasoft/ewol/widget/Container.java b/src/org/atriasoft/ewol/widget/Container.java index c9c314e..48e3ee8 100644 --- a/src/org/atriasoft/ewol/widget/Container.java +++ b/src/org/atriasoft/ewol/widget/Container.java @@ -24,8 +24,7 @@ public class Container extends Widget { /** * Constructor */ - public Container() { - } + public Container() {} @Override public void calculateMinMaxSize() { @@ -145,7 +144,7 @@ public class Container extends Widget { @Override public void onRegenerateDisplay() { if (this.subWidget != null) { - this.subWidget.onRegenerateDisplay(); + this.subWidget.systemRegenerateDisplay(); } } diff --git a/src/org/atriasoft/ewol/widget/ContainerN.java b/src/org/atriasoft/ewol/widget/ContainerN.java index 761204e..8d9da0a 100644 --- a/src/org/atriasoft/ewol/widget/ContainerN.java +++ b/src/org/atriasoft/ewol/widget/ContainerN.java @@ -205,7 +205,7 @@ public class ContainerN extends Widget { public void onRegenerateDisplay() { for (Widget it : this.subWidget) { if (it != null) { - it.onRegenerateDisplay(); + it.systemRegenerateDisplay(); } } } diff --git a/src/org/atriasoft/ewol/widget/Entry.java b/src/org/atriasoft/ewol/widget/Entry.java new file mode 100644 index 0000000..7c74695 --- /dev/null +++ b/src/org/atriasoft/ewol/widget/Entry.java @@ -0,0 +1,761 @@ +package org.atriasoft.ewol.widget; + +import java.util.Arrays; +import java.util.regex.Pattern; + +import org.atriasoft.esignal.Connection; +import org.atriasoft.esignal.Signal; +import org.atriasoft.esignal.SignalEmpty; +import org.atriasoft.etk.Uri; +import org.atriasoft.etk.math.FMath; +import org.atriasoft.etk.math.Vector2f; +import org.atriasoft.ewol.Padding; +import org.atriasoft.ewol.annotation.EwolDescription; +import org.atriasoft.ewol.annotation.EwolSignal; +import org.atriasoft.ewol.compositing.CompositingText; +import org.atriasoft.ewol.compositing.GuiShape; +import org.atriasoft.ewol.event.EventEntry; +import org.atriasoft.ewol.event.EventInput; +import org.atriasoft.ewol.event.EventTime; +import org.atriasoft.ewol.internal.Log; +import org.atriasoft.exml.annotation.XmlManaged; +import org.atriasoft.exml.annotation.XmlName; +import org.atriasoft.exml.annotation.XmlProperty; +import org.atriasoft.gale.context.ClipBoard; +import org.atriasoft.gale.context.ClipboardList; +import org.atriasoft.gale.key.KeyKeyboard; +import org.atriasoft.gale.key.KeyStatus; +import org.atriasoft.gale.key.KeyType; + +/** + * @ingroup ewolWidgetGroup + * Entry box display : + * + * ~~~~~~~~~~~~~~~~~~~~~~ + * ---------------------------------------------- + * | Editable Text | + * ---------------------------------------------- + * ~~~~~~~~~~~~~~~~~~~~~~ + */ +public class Entry extends Widget { + //private int colorIdCursor; //!< color property of the text cursor + //private int colorIdSelection; //!< color property of the text selection + //private int colorIdTextBg; //!< color property of the text background + + private int colorIdTextFg; //!< color property of the text foreground + + private boolean displayCursor = false; //!< Cursor must be display only when the widget has the focus + + private int displayCursorPos = 2; //!< Cursor position in number of Char + + private int displayCursorPosSelection = 2; //!< Selection position end (can be befor or after cursor and == this.displayCursorPos chan no selection availlable + private int displayStartPosition = 0; //!< offset in pixel of the display of the UString + private boolean needUpdateTextPos = true; //!< text position can have change + protected Connection periodicConnectionHanble; //!< Periodic call handle to remove it when needed + @XmlManaged + @XmlProperty + @XmlName(value = "config") + @EwolDescription(value = "configuration of the widget") + private Uri propertyConfig = new Uri("THEME", "shape/Entry.json", "ewol"); + @XmlManaged + @XmlProperty + @XmlName(value = "max") + @EwolDescription(value = "Maximum char that can be set on the Entry") + private int propertyMaxCharacter = Integer.MAX_VALUE; //!< number max of Character in the list + @XmlManaged + @XmlProperty + @XmlName(value = "password") + @EwolDescription(value = "Not display content in password mode") + private boolean propertyPassword = false; //!< Disable display of the content of the entry + /// regular expression value + @XmlManaged + @XmlProperty + @XmlName(value = "regex") + @EwolDescription(value = "Control what it is write with a regular expression") + private String propertyRegex = ".*"; + /// Text to display when nothing in in the entry (decorated text...) + @XmlManaged + @XmlProperty + @XmlName(value = "empty-text") + @EwolDescription(value = "Text when nothing is written") + private String propertyTextWhenNothing = null; + + @XmlManaged + @XmlProperty + @XmlName(value = "value") + @EwolDescription(value = "Value display in the entry (decorated text)") + private String propertyValue = "Test Text..."; //!< string that must be displayed + + private Pattern regex = null; //!< regular expression to check content + + private GuiShape shape; + //.create() + @EwolSignal(name = "click", description = "the user Click on the Entry box") + public SignalEmpty signalClick = new SignalEmpty(); //!< bang on click the entry box + @EwolSignal(name = "enter", description = "The cursor enter inside the button") + public Signal signalEnter = new Signal<>(); //!< Enter key is pressed + @EwolSignal(name = "modify", description = "Entry box value change") + public Signal signalModify = new Signal<>(); //!< data change + private final CompositingText text = new CompositingText(); //!< text display this.text + + /** + * Contuctor + * @param _newData The USting that might be set in the Entry box (no event generation!!) + */ + public Entry() { + this.propertyCanFocus = true; + onChangePropertyShaper(); + + this.regex = Pattern.compile(this.propertyRegex); + if (this.regex == null) { + Log.error("can not parse regex for : " + this.propertyRegex); + } + markToRedraw(); + shortCutAdd("ctrl+w", "clean"); + shortCutAdd("ctrl+x", "cut"); + shortCutAdd("ctrl+c", "copy"); + shortCutAdd("ctrl+v", "paste"); + shortCutAdd("ctrl+a", "select:all"); + shortCutAdd("ctrl+shift+a", "select:none"); + this.shape = new GuiShape(this.propertyConfig); + //TODO this.signalShortcut.connect(this, Entry::onCallbackShortCut); + } + + @Override + public void calculateMinMaxSize() { + // call main class + super.calculateMinMaxSize(); + // get generic padding + Padding padding = Padding.ZERO; + if (this.shape != null) { + padding = this.shape.getPadding(); + } + int minHeight = (int) this.text.getHeight();//calculateSize('A').y(); + + Vector2f minimumSizeBase = new Vector2f(20, minHeight); + // add padding : + minimumSizeBase = minimumSizeBase.add(padding.x(), padding.y()); + this.minSize = Vector2f.max(this.minSize, minimumSizeBase); + // verify the min max of the min size ... + checkMinSize(); + Log.error("min size = " + this.minSize); + } + + protected void changeStatusIn(final int newStatusId) { + /* + if (this.shaper.changeStatusIn(_newStatusId)) { + this.periodicConnectionHanble = EwolObject.getObjectManager().periodicCall.connect(this, ewol::widget::Entry::periodicCall); + markToRedraw(); + } + */ + } + + /** + * Copy the selected data on the specify clipboard + * @param clipboardID Selected clipboard + */ + public void copySelectionToClipBoard(final ClipboardList clipboardID) { + if (this.displayCursorPosSelection == this.displayCursorPos) { + // nothing to cut ... + return; + } + int pos1 = this.displayCursorPosSelection; + int pos2 = this.displayCursorPos; + if (this.displayCursorPosSelection > this.displayCursorPos) { + pos2 = this.displayCursorPosSelection; + pos1 = this.displayCursorPos; + } + // Copy + String tmpData = this.propertyValue.substring(pos1, pos2); + ClipBoard.set(clipboardID, tmpData); + } + + public Uri getPropertyConfig() { + return this.propertyConfig; + } + + public int getPropertyMaxCharacter() { + return this.propertyMaxCharacter; + } + + public String getPropertyRegex() { + return this.propertyRegex; + } + + public String getPropertyTextWhenNothing() { + return this.propertyTextWhenNothing; + } + + public String getPropertyValue() { + return this.propertyValue; + } + + public boolean isPropertyPassword() { + return this.propertyPassword; + } + + /** + * informe the system thet the text change and the start position change + */ + protected void markToUpdateTextPosition() { + this.needUpdateTextPos = true; + } + + private void onCallbackCopy() { + copySelectionToClipBoard(ClipboardList.CLIPBOARD_STD); + } + + private void onCallbackCut() { + copySelectionToClipBoard(ClipboardList.CLIPBOARD_STD); + removeSelected(); + this.signalModify.emit(this.propertyValue); + } + + private void onCallbackEntryClean() { + this.propertyValue = ""; + this.displayStartPosition = 0; + this.displayCursorPos = 0; + this.displayCursorPosSelection = this.displayCursorPos; + markToRedraw(); + } + + private void onCallbackPaste() { + ClipBoard.request(ClipboardList.CLIPBOARD_STD); + } + + private void onCallbackSelect(final boolean all) { + if (all) { + this.displayCursorPosSelection = 0; + this.displayCursorPos = this.propertyValue.length(); + } else { + this.displayCursorPosSelection = this.displayCursorPos; + } + markToRedraw(); + } + + private void onCallbackShortCut(final String value) { + if (value.equals("clean")) { + onCallbackEntryClean(); + } else if (value.equals("cut")) { + onCallbackCut(); + } else if (value.equals("copy")) { + onCallbackCopy(); + } else if (value.equals("paste")) { + Log.warning("Request past ..."); + onCallbackPaste(); + } else if (value.equals("select:all")) { + onCallbackSelect(true); + } else if (value.equals("select:none")) { + onCallbackSelect(false); + } else { + Log.warning("Unknow event from ShortCut : " + value); + } + } + + protected void onChangePropertyMaxCharacter() { + // TODO : check number of char in the data + } + + protected void onChangePropertyPassword() { + markToRedraw(); + } + + protected void onChangePropertyRegex() { + this.regex = Pattern.compile(this.propertyRegex); + if (this.regex != null) { + Log.error("can not parse regex for : " + this.propertyRegex); + } + markToRedraw(); + } + + protected void onChangePropertyShaper() { + if (this.shape == null) { + this.shape = new GuiShape(this.propertyConfig); + } else { + this.shape.setSource(this.propertyConfig); + } + // this.colorIdTextFg = this.shape.requestColor("text-foreground"); + // this.colorIdTextBg = this.shape.requestColor("text-background"); + // this.colorIdCursor = this.shape.requestColor("text-cursor"); + // this.colorIdSelection = this.shape.requestColor("text-selection"); + } + + protected void onChangePropertyTextWhenNothing() { + markToRedraw(); + } + + protected void onChangePropertyValue() { + String newData = this.propertyValue; + if ((long) newData.length() > this.propertyMaxCharacter) { + newData = newData.substring(0, this.propertyMaxCharacter); + Log.debug("Limit entry set of data... " + newData); + } + // set the value with the check of the RegExp ... + setInternalValue(newData); + if (newData == this.propertyValue) { + this.displayCursorPos = this.propertyValue.length(); + this.displayCursorPosSelection = this.displayCursorPos; + Log.verbose("Set : '" + newData + "'"); + } + markToRedraw(); + } + + @Override + protected void onDraw() { + if (this.shape != null) { + this.shape.draw(); + } + this.text.draw(); + } + + @Override + public void onEventClipboard(final ClipboardList clipboardID) { + // remove curent selected data ... + removeSelected(); + // get current selection / Copy : + String tmpData = ClipBoard.get(clipboardID); + // add it on the current display: + if (tmpData.length() != 0) { + StringBuilder newData = new StringBuilder(this.propertyValue); + newData.insert(this.displayCursorPos, tmpData.charAt(0)); + setInternalValue(newData.toString()); + if (this.propertyValue.equals(newData.toString())) { + if (this.propertyValue.length() == tmpData.length()) { + this.displayCursorPos = tmpData.length(); + } else { + this.displayCursorPos += tmpData.length(); + } + this.displayCursorPosSelection = this.displayCursorPos; + markToRedraw(); + } + } + this.signalModify.emit(this.propertyValue); + } + + @Override + public boolean onEventEntry(final EventEntry event) { + Log.warning("Event on Entry ... " + event); + if (event.type() == KeyKeyboard.CHARACTER) { + if (event.status() == KeyStatus.down) { + // remove current selected data ... + removeSelected(); + if (event.getChar() == '\n' || event.getChar() == '\r') { + this.signalEnter.emit(this.propertyValue); + return true; + } + if (event.getChar() == 0x7F) { + // SUPPR : + if (this.propertyValue.length() > 0 && this.displayCursorPos < (long) this.propertyValue.length()) { + StringBuilder newData = new StringBuilder(this.propertyValue); + newData.deleteCharAt(this.displayCursorPos); + this.propertyValue = newData.toString(); + this.displayCursorPos = Math.max(this.displayCursorPos, 0); + this.displayCursorPosSelection = this.displayCursorPos; + } + } else if (event.getChar() == 0x08) { + // DEL : + if (this.propertyValue.length() > 0 && this.displayCursorPos != 0) { + StringBuilder newData = new StringBuilder(this.propertyValue); + newData.deleteCharAt(this.displayCursorPos - 1); + this.propertyValue = newData.toString(); + this.displayCursorPos--; + this.displayCursorPos = Math.max(this.displayCursorPos, 0); + this.displayCursorPosSelection = this.displayCursorPos; + } + } else if (event.getChar() >= 20) { + Log.error("get data: '" + event.getChar() + "' = '" + event.getChar() + "'"); + if ((long) this.propertyValue.length() > this.propertyMaxCharacter) { + Log.info("Reject data for entry : '" + event.getChar() + "'"); + } else { + StringBuilder newData = new StringBuilder(this.propertyValue); + newData.insert(this.displayCursorPos, event.getChar()); + setInternalValue(newData.toString()); + if (this.propertyValue.equals(newData)) { + this.displayCursorPos += 1;//inputData.length(); + this.displayCursorPosSelection = this.displayCursorPos; + } + } + } + this.signalModify.emit(this.propertyValue); + markToRedraw(); + return true; + } + return false; + } + if (event.status() == KeyStatus.down) { + switch (event.type()) { + case LEFT: + this.displayCursorPos--; + break; + case RIGHT: + this.displayCursorPos++; + break; + case START: + this.displayCursorPos = 0; + break; + case END: + this.displayCursorPos = this.propertyValue.length(); + break; + default: + return false; + } + this.displayCursorPos = FMath.avg(0, this.displayCursorPos, this.propertyValue.length()); + this.displayCursorPosSelection = this.displayCursorPos; + markToRedraw(); + return true; + } + return false; + } + + @Override + public boolean onEventInput(final EventInput event) { + Log.warning("Event on Input ... " + event); + if (event.inputId() == 1) { + if (KeyStatus.pressSingle == event.status()) { + keepFocus(); + this.signalClick.emit(); + //nothing to do ... + return true; + } + if (KeyStatus.pressDouble == event.status()) { + keepFocus(); + // select word + this.displayCursorPosSelection = this.displayCursorPos - 1; + // search forward + for (int iii = this.displayCursorPos; iii <= this.propertyValue.length(); iii++) { + if (iii == this.propertyValue.length()) { + this.displayCursorPos = iii; + break; + } + if (!((this.propertyValue.charAt(iii) >= 'a' && this.propertyValue.charAt(iii) <= 'z') || (this.propertyValue.charAt(iii) >= 'A' && this.propertyValue.charAt(iii) <= 'Z') + || (this.propertyValue.charAt(iii) >= '0' && this.propertyValue.charAt(iii) <= '9') || this.propertyValue.charAt(iii) == '_' || this.propertyValue.charAt(iii) == '-')) { + this.displayCursorPos = iii; + break; + } + } + // search backward + for (int iii = this.displayCursorPosSelection; iii >= -1; iii--) { + if (iii == -1) { + this.displayCursorPosSelection = 0; + break; + } + if (!((this.propertyValue.charAt(iii) >= 'a' && this.propertyValue.charAt(iii) <= 'z') || (this.propertyValue.charAt(iii) >= 'A' && this.propertyValue.charAt(iii) <= 'Z') + || (this.propertyValue.charAt(iii) >= '0' && this.propertyValue.charAt(iii) <= '9') || this.propertyValue.charAt(iii) == '_' || this.propertyValue.charAt(iii) == '-')) { + this.displayCursorPosSelection = iii + 1; + break; + } + } + // Copy to clipboard Middle ... + copySelectionToClipBoard(ClipboardList.CLIPBOARD_SELECTION); + markToRedraw(); + } else if (KeyStatus.pressTriple == event.status()) { + keepFocus(); + this.displayCursorPosSelection = 0; + this.displayCursorPos = this.propertyValue.length(); + } else if (KeyStatus.down == event.status()) { + keepFocus(); + updateCursorPosition(event.pos()); + markToRedraw(); + } else if (KeyStatus.move == event.status()) { + keepFocus(); + updateCursorPosition(event.pos(), true); + markToRedraw(); + } else if (KeyStatus.up == event.status()) { + keepFocus(); + updateCursorPosition(event.pos(), true); + // Copy to clipboard Middle ... + copySelectionToClipBoard(ClipboardList.CLIPBOARD_SELECTION); + markToRedraw(); + } + } else if (KeyType.mouse == event.type() && event.inputId() == 2) { + if (event.status() == KeyStatus.down || event.status() == KeyStatus.move || event.status() == KeyStatus.up) { + keepFocus(); + // updatethe cursor position : + updateCursorPosition(event.pos()); + } + // Paste current selection only when up button + if (event.status() == KeyStatus.up) { + keepFocus(); + // middle button => past data... + ClipBoard.request(ClipboardList.CLIPBOARD_SELECTION); + } + } + return false; + } + + @Override + protected void onGetFocus() { + this.displayCursor = true; + //changeStatusIn(STATUS_SELECTED); + showKeyboard(); + markToRedraw(); + } + + @Override + protected void onLostFocus() { + this.displayCursor = false; + //changeStatusIn(STATUS_NORMAL); + hideKeyboard(); + markToRedraw(); + } + + @Override + public void onRegenerateDisplay() { + if (!needRedraw()) { + //return; + } + //Log.verbose("Regenerate Display ==> is needed: '" + this.propertyValue + "'"); + this.shape.clear(); + this.text.clear(); + if (this.colorIdTextFg >= 0) { + //this.text.setDefaultColorFg(this.shape.getColor(this.colorIdTextFg)); + //this.text.setDefaultColorBg(this.shape.getColor(this.colorIdTextBg)); + //this.text.setCursorColor(this.shape.getColor(this.colorIdCursor)); + //this.text.setSelectionColor(this.shape.getColor(this.colorIdSelection)); + } + updateTextPosition(); + Padding padding = this.shape.getPadding(); + + Vector2f tmpSizeShaper = this.minSize; + if (this.propertyFill.x()) { + tmpSizeShaper = tmpSizeShaper.withX(this.size.x()); + } + if (this.propertyFill.y()) { + tmpSizeShaper = tmpSizeShaper.withY(this.size.y()); + } + + Vector2f tmpOriginShaper = this.size.less(tmpSizeShaper).multiply(0.5f); + Vector2f tmpSizeText = tmpSizeShaper.less(padding.x(), padding.y()); + Vector2f tmpOriginText = this.size.less(tmpSizeText).multiply(0.5f); + // sometimes, the user define an height bigger than the real size needed == > in this case we need to center the text in the shaper ... + int minHeight = (int) this.text.getHeight(); + if (tmpSizeText.y() > minHeight) { + tmpOriginText = tmpOriginText.add(0, (tmpSizeText.y() - minHeight) * 0.5f); + } + // fix all the position in the int class: + tmpSizeShaper = Vector2f.clipInt(tmpSizeShaper); + tmpOriginShaper = Vector2f.clipInt(tmpOriginShaper); + tmpSizeText = Vector2f.clipInt(tmpSizeText); + tmpOriginText = Vector2f.clipInt(tmpOriginText); + + this.text.reset(); + this.text.setClippingWidth(tmpOriginText, tmpSizeText); + this.text.setPos(tmpOriginText.add(this.displayStartPosition, 0)); + if (this.displayCursorPosSelection != this.displayCursorPos) { + this.text.setCursorSelection(this.displayCursorPos, this.displayCursorPosSelection); + } else { + this.text.setCursorPos(this.displayCursorPos); + } + char[] valueToDisplay = this.propertyValue.toCharArray(); + if (this.propertyPassword) { + Arrays.fill(valueToDisplay, '*'); + } + + if (valueToDisplay.length != 0) { + this.text.print(new String(valueToDisplay)); + } else if (this.propertyTextWhenNothing != null) { + this.text.printDecorated(this.propertyTextWhenNothing); + } + this.text.setClippingMode(false); + + this.shape.setShape(tmpOriginShaper, tmpSizeShaper, tmpOriginText, tmpSizeText); + this.text.flush(); + this.shape.flush(); + + } + + /** + * Periodic call to update grapgic display + * @param _event Time generic event + */ + protected void periodicCall(final EventTime event) { + if (!this.shape.periodicCall(event)) { + this.periodicConnectionHanble.disconnect(); + } + markToRedraw(); + } + + /** + * remove the selected area + * @note This request a regeneration of the display + */ + public void removeSelected() { + if (this.displayCursorPosSelection == this.displayCursorPos) { + // nothing to cut ... + return; + } + int pos1 = this.displayCursorPosSelection; + int pos2 = this.displayCursorPos; + if (this.displayCursorPosSelection > this.displayCursorPos) { + pos2 = this.displayCursorPosSelection; + pos1 = this.displayCursorPos; + } + // remove data ... + this.displayCursorPos = pos1; + this.displayCursorPosSelection = pos1; + StringBuilder tmp = new StringBuilder(this.propertyValue); + tmp.delete(pos1, pos2 - pos1); + this.propertyValue = tmp.toString(); + markToRedraw(); + } + + /** + * internal check the value with RegExp checking + * @param newData The new string to display + */ + protected void setInternalValue(final String newData) { + String previous = this.propertyValue; + // check the RegExp : + if (newData.length() > 0) { + /* + if (this.regex.parse(_newData, 0, _newData.size()) == false) { + Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "'" ); + return; + } + if (this.regex.start() != 0) { + Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "' (start position error)" ); + return; + } + if (this.regex.stop() != _newData.size()) { + Log.info("The input data does not match with the regExp '" + _newData + "' Regex='" + propertyRegex + "' (stop position error)" ); + return; + } + */ + } + this.propertyValue = newData; + markToRedraw(); + } + + public void setPropertyConfig(final Uri propertyConfig) { + if (this.propertyConfig.equals(propertyConfig)) { + return; + } + this.propertyConfig = propertyConfig; + onChangePropertyShaper(); + } + + public void setPropertyMaxCharacter(final int propertyMaxCharacter) { + if (this.propertyMaxCharacter == propertyMaxCharacter) { + return; + } + this.propertyMaxCharacter = propertyMaxCharacter; + onChangePropertyMaxCharacter(); + } + + public void setPropertyPassword(final boolean propertyPassword) { + if (this.propertyPassword == propertyPassword) { + return; + } + this.propertyPassword = propertyPassword; + onChangePropertyPassword(); + } + + public void setPropertyRegex(final String propertyRegex) { + if (this.propertyRegex.equals(propertyRegex)) { + return; + } + this.propertyRegex = propertyRegex; + onChangePropertyRegex(); + } + + public void setPropertyTextWhenNothing(final String propertyTextWhenNothing) { + if (this.propertyTextWhenNothing.equals(propertyTextWhenNothing)) { + return; + } + this.propertyTextWhenNothing = propertyTextWhenNothing; + onChangePropertyTextWhenNothing(); + } + + public void setPropertyValue(final String propertyValue) { + if (this.propertyValue.equals(propertyValue)) { + return; + } + this.propertyValue = propertyValue; + onChangePropertyValue(); + } + + /** + * change the cursor position with the curent position requested on the display + * @param pos Absolute position of the event + * @note The display is automaticly requested when change apear. + */ + protected void updateCursorPosition(final Vector2f pos) { + updateCursorPosition(pos, false); + } + + protected void updateCursorPosition(final Vector2f pos, final boolean selection/*=false*/) { + Padding padding = this.shape.getPadding(); + + Vector2f relPos = relativePosition(pos); + relPos = relPos.withX(relPos.x() - this.displayStartPosition - padding.left()); + // try to find the new cursor position : + String tmpDisplay = this.propertyValue.substring(0, this.displayStartPosition); + int displayHidenSize = (int) this.text.calculateSize(tmpDisplay).x(); + //Log.debug("hidenSize : " + displayHidenSize); + int newCursorPosition = -1; + int tmpTextOriginX = (int) padding.left(); + for (int iii = 0; iii < this.propertyValue.length(); iii++) { + tmpDisplay = this.propertyValue.substring(0, iii); + int tmpWidth = (int) (this.text.calculateSize(tmpDisplay).x() - displayHidenSize); + if (tmpWidth >= relPos.x() - tmpTextOriginX) { + newCursorPosition = iii; + break; + } + } + if (newCursorPosition == -1) { + newCursorPosition = this.propertyValue.length(); + } + if (!selection) { + this.displayCursorPos = newCursorPosition; + this.displayCursorPosSelection = this.displayCursorPos; + markToRedraw(); + } else { + if (this.displayCursorPos == this.displayCursorPosSelection) { + this.displayCursorPosSelection = this.displayCursorPos; + } + this.displayCursorPos = newCursorPosition; + markToRedraw(); + } + markToUpdateTextPosition(); + } + + /** + * update the display position start == > depending of the position of the Cursor and the size of the Data inside + * @change this.displayStartPosition < == updated + */ + protected void updateTextPosition() { + if (!this.needUpdateTextPos) { + return; + } + Padding padding = this.shape.getPadding(); + + int tmpSizeX = (int) this.minSize.x(); + if (this.propertyFill.x()) { + tmpSizeX = (int) this.size.x(); + } + int tmpUserSize = (int) (tmpSizeX - padding.x()); + int totalWidth = (int) this.text.calculateSize(this.propertyValue).x(); + // Check if the data inside the display can be contain in the entry box + if (totalWidth < tmpUserSize) { + // all can be display : + this.displayStartPosition = 0; + } else { + // all can not be set : + String tmpDisplay = this.propertyValue.substring(0, this.displayCursorPos); + int pixelCursorPos = (int) this.text.calculateSize(tmpDisplay).x(); + // check if the Cussor is visible at 10px nearest the border : + int tmp1 = pixelCursorPos + this.displayStartPosition; + Log.debug("cursorPos=" + pixelCursorPos + "px maxSize=" + tmpUserSize + "px tmp1=" + tmp1); + if (tmp1 < 10) { + // set the cursor on le left + this.displayStartPosition = Math.min(-pixelCursorPos + 10, 0); + } else if (tmp1 > tmpUserSize - 10) { + // set the cursor of the Right + this.displayStartPosition = Math.min(-pixelCursorPos + tmpUserSize - 10, 0); + } + // else : the cursor is inside the display + //this.displayStartPosition = -totalWidth + tmpUserSize; + } + } + +} diff --git a/src/org/atriasoft/ewol/widget/ImageDisplay.java b/src/org/atriasoft/ewol/widget/ImageDisplay.java index e0f2d5c..bbae8cc 100644 --- a/src/org/atriasoft/ewol/widget/ImageDisplay.java +++ b/src/org/atriasoft/ewol/widget/ImageDisplay.java @@ -5,7 +5,7 @@ */ package org.atriasoft.ewol.widget; -import org.atriasoft.egami.Image; +import org.atriasoft.egami.ImageByteRGBA; import org.atriasoft.esignal.SignalEmpty; import org.atriasoft.etk.Dimension; import org.atriasoft.etk.Uri; @@ -280,7 +280,7 @@ public class ImageDisplay extends Widget { * Set an image with direct elements * @param image Image to set in the display */ - public void setCustumSource(final Image image) { + public void setCustumSource(final ImageByteRGBA image) { // TODO : Better interfacing of all element internal ==> this is a temporary prototype this.compositing.setSource(image); markToRedraw(); diff --git a/src/org/atriasoft/ewol/widget/Label.java b/src/org/atriasoft/ewol/widget/Label.java index 4f26307..4270415 100644 --- a/src/org/atriasoft/ewol/widget/Label.java +++ b/src/org/atriasoft/ewol/widget/Label.java @@ -137,7 +137,7 @@ public class Label extends Widget { @Override public void onRegenerateDisplay() { if (!needRedraw()) { - return; + //return; } this.text.clear(); int paddingSize = 2; @@ -155,7 +155,7 @@ public class Label extends Widget { Vector2i localSize = new Vector2i((int) this.minSize.x(), (int) this.minSize.y()); - // no change for the text orogin : + // no change for the text origin : Vector3f tmpTextOrigin = new Vector3f((this.size.x() - this.minSize.x()) / 2.0f, (this.size.y() - this.minSize.y()) / 2.0f, 0); if (this.propertyFill.x()) { diff --git a/src/org/atriasoft/ewol/widget/Spacer.java b/src/org/atriasoft/ewol/widget/Spacer.java index 83f2965..b3a6986 100644 --- a/src/org/atriasoft/ewol/widget/Spacer.java +++ b/src/org/atriasoft/ewol/widget/Spacer.java @@ -45,7 +45,6 @@ public class Spacer extends Widget { @Override public void onDraw() { this.draw.draw(); - this.draw.flush(); } @Override diff --git a/src/org/atriasoft/ewol/widget/Widget.java b/src/org/atriasoft/ewol/widget/Widget.java index c7eeb97..df5c155 100644 --- a/src/org/atriasoft/ewol/widget/Widget.java +++ b/src/org/atriasoft/ewol/widget/Widget.java @@ -10,6 +10,7 @@ import java.util.ArrayList; import java.util.List; import org.atriasoft.esignal.Signal; +import org.atriasoft.etk.Color; import org.atriasoft.etk.Dimension; import org.atriasoft.etk.Distance; import org.atriasoft.etk.math.FMath; @@ -22,6 +23,7 @@ import org.atriasoft.ewol.DrawProperty; import org.atriasoft.ewol.Gravity; import org.atriasoft.ewol.annotation.EwolDescription; import org.atriasoft.ewol.annotation.EwolSignal; +import org.atriasoft.ewol.compositing.CompositingDrawing; import org.atriasoft.ewol.event.EntrySystem; import org.atriasoft.ewol.event.EventEntry; import org.atriasoft.ewol.event.EventInput; @@ -55,9 +57,10 @@ public class Widget extends EwolObject { // -- keyboard event properties Area // ---------------------------------------------------------------------------------------------------------------- private boolean allowRepeatKeyboardEvent = true; //!< This remove the repeating keybord event due to the ant pressing key. - private Cursor cursorDisplay = Cursor.arrow; + private final CompositingDrawing drawDebugBorder = new CompositingDrawing(); //!< Compositing drawing element + // grab cursor mode private boolean grabCursor = false; @@ -484,7 +487,7 @@ public class Widget extends EwolObject { */ public boolean onEventShortCut(final KeySpecial special, Character unicodeValue, final KeyKeyboard kbMove, final boolean isDown) { unicodeValue = Character.toLowerCase(unicodeValue); - Log.verbose("check shortcut...." + special + " " + unicodeValue + " " + kbMove + " " + (isDown ? "DOWN" : "UP") + " nb shortcut:" + this.localShortcut.size()); + //Log.verbose("check shortcut...." + special + " " + unicodeValue + " " + kbMove + " " + (isDown ? "DOWN" : "UP") + " nb shortcut:" + this.localShortcut.size()); // Remove the up event of the shortcut... if (!isDown) { for (int iii = this.localShortcut.size() - 1; iii >= 0; iii--) { @@ -527,10 +530,7 @@ public class Widget extends EwolObject { */ protected void onLostFocus() {} - /** - * Event generated when a redraw is needed - */ - public void onRegenerateDisplay() {} + protected void onRegenerateDisplay() {} protected void onUpdateMinMaxSize() { final Vector2f pixelMin = this.propertyMinSize.getPixel(); @@ -927,12 +927,15 @@ public class Widget extends EwolObject { // Scale if needed (feature not validate) final Matrix4f tmpScale = Matrix4f.createMatrixScale(this.zoom, this.zoom, 1.0f); // create orthogonal projection for GUI ==> simple to manage staking - Matrix4f tmpProjection = Matrix4f.createMatrixOrtho(-tmpSize.size().x() / 2, tmpSize.size().x() / 2, -tmpSize.size().y() / 2, tmpSize.size().y() / 2, -50, 50); - Matrix4f tmpMat = tmpProjection.multiply(tmpScale).multiply(tmpTranslate); + Matrix4f tmpProjection = Matrix4f.createMatrixOrtho(-tmpSize.size().x() / 2, tmpSize.size().x() / 2, -tmpSize.size().y() / 2, tmpSize.size().y() / 2, -500, 500); + //Matrix4f tmpMat = tmpProjection.multiply(tmpScale).multiply(tmpTranslate); OpenGL.push(); // set internal matrix system : - OpenGL.setMatrix(tmpMat); + //OpenGL.setMatrix(tmpMat); + OpenGL.setMatrix(tmpProjection); + OpenGL.setCameraMatrix(tmpScale.multiply(tmpTranslate)); + this.drawDebugBorder.draw(); //long startTime = ewol::getTime(); onDraw(); OpenGL.pop(); @@ -961,15 +964,43 @@ public class Widget extends EwolObject { * @return false the event is not used */ public boolean systemEventInput(final InputSystem event) { - final Widget up = (Widget) this.parent.get(); - if (up != null) { - if (up.systemEventInput(event)) { - return true; + if (this.parent != null) { + final Widget up = (Widget) this.parent.get(); + if (up != null) { + if (up.systemEventInput(event)) { + return true; + } } } return onEventInput(event.event()); } + /** + * Event generated when a redraw is needed + */ + public void systemRegenerateDisplay() { + if (this.drawDebugBorder != null) { + this.drawDebugBorder.clear(); + this.drawDebugBorder.setColor(Color.RED); + this.drawDebugBorder.setPos(1, 1); + this.drawDebugBorder.setThickness(1); + this.drawDebugBorder.lineRel(this.size.x() - 2, 0); // TODO PB with the thickness when draw rectangle ... + this.drawDebugBorder.setPos(this.size.x() - 1, 1); + this.drawDebugBorder.lineRel(0, this.size.y() - 2); + this.drawDebugBorder.setPos(this.size.x() - 1, this.size.y() - 1); + this.drawDebugBorder.lineRel(-this.size.x() - 2, 0); + this.drawDebugBorder.setPos(1, this.size.y() - 1); + this.drawDebugBorder.lineRel(0, -this.size.y() - 2); + /* + this.drawDebugBorder.setColor(Color.BLUE); + this.drawDebugBorder.setPos(3, 3); + this.drawDebugBorder.rectangleWidth(new Vector3f(this.size.x() - 6, this.size.y() - 6, 0)); + */ + this.drawDebugBorder.flush(); + } + onRegenerateDisplay(); + } + /** * Un-Grab the cursor (default mode cursor offset) */ diff --git a/src/org/atriasoft/ewol/widget/Windows.java b/src/org/atriasoft/ewol/widget/Windows.java index 6548427..7339f74 100644 --- a/src/org/atriasoft/ewol/widget/Windows.java +++ b/src/org/atriasoft/ewol/widget/Windows.java @@ -157,11 +157,11 @@ public class Windows extends Widget { @Override public void onRegenerateDisplay() { if (this.subWidget != null) { - this.subWidget.onRegenerateDisplay(); + this.subWidget.systemRegenerateDisplay(); } for (Widget it : this.popUpWidgetList) { if (it != null) { - it.onRegenerateDisplay(); + it.systemRegenerateDisplay(); } } }